Merge branch 'master' into jdbc-impersonation

This commit is contained in:
astroshim 2016-11-14 13:24:03 +09:00
commit 59aa9ff269
24 changed files with 677 additions and 488 deletions

318
README.md
View file

@ -17,323 +17,13 @@ Core feature:
To know more about Zeppelin, visit our web site [http://zeppelin.apache.org](http://zeppelin.apache.org)
## Requirements
* Git
* Java 1.7
* Tested on Mac OSX, Ubuntu 14.X, CentOS 6.X, Windows 7 Pro SP1
* Maven (if you want to build from the source code)
* Node.js Package Manager (npm, downloaded by Maven during build phase)
## Getting Started
### Before Build
If you don't have requirements prepared, install it.
(The installation method may vary according to your environment, example is for Ubuntu.)
### Install binary package
Please go to [install](http://zeppelin.apache.org/docs/snapshot/install/install.html) to install Apache Zeppelin from binary package.
```
sudo apt-get update
sudo apt-get install git
sudo apt-get install openjdk-7-jdk
sudo apt-get install npm
sudo apt-get install libfontconfig
```
### Build from source
Please check [Build from source](http://zeppelin.apache.org/docs/snapshot/install/build.html) to build Zeppelin from source.
#### Proxy settings (optional)
First of all, set your proxy configuration on Maven `settings.xml`.
```
<settings>
<proxies>
<proxy>
<id>proxy-http</id>
<active>true</active>
<protocol>http</protocol>
<host>localhost</host>
<port>3128</port>
<!-- <username>usr</username>
<password>pwd</password> -->
<nonProxyHosts>localhost|127.0.0.1</nonProxyHosts>
</proxy>
<proxy>
<id>proxy-https</id>
<active>true</active>
<protocol>https</protocol>
<host>localhost</host>
<port>3128</port>
<!-- <username>usr</username>
<password>pwd</password> -->
<nonProxyHosts>localhost|127.0.0.1</nonProxyHosts>
</proxy>
</proxies>
</settings>
```
Then, run these commands from shell.
```
npm config set proxy http://localhost:3128
npm config set https-proxy http://localhost:3128
npm config set registry "http://registry.npmjs.org/"
npm config set strict-ssl false
git config --global http.proxy http://localhost:3128
git config --global https.proxy http://localhost:3128
git config --global url."http://".insteadOf git://
```
Cleanup: set `active false` in Maven `settings.xml` and run these commands.
```
npm config rm proxy
npm config rm https-proxy
git config --global --unset http.proxy
git config --global --unset https.proxy
git config --global --unset url."http://".insteadOf
```
_Notes:_
- If you are behind NTLM proxy you can use [Cntlm Authentication Proxy](http://cntlm.sourceforge.net/).
- Replace `localhost:3128` with the standard pattern `http://user:pwd@host:port`.
#### Install maven
```
wget http://www.eu.apache.org/dist/maven/maven-3/3.3.9/binaries/apache-maven-3.3.9-bin.tar.gz
sudo tar -zxf apache-maven-3.3.9-bin.tar.gz -C /usr/local/
sudo ln -s /usr/local/apache-maven-3.3.9/bin/mvn /usr/local/bin/mvn
```
_Notes:_
- Ensure node is installed by running `node --version`
- Ensure maven is running version 3.1.x or higher with `mvn -version`
- Configure maven to use more memory than usual by `export MAVEN_OPTS="-Xmx2g -XX:MaxPermSize=1024m"`
### Build
If you want to build Zeppelin from the source, please first clone this repository, then:
```
mvn clean package -DskipTests [Options]
```
Each Interpreter requires different Options.
#### Spark Interpreter
To build with a specific Spark version, Hadoop version or specific features, define one or more of the following profiles and options:
##### `-Pspark-[version]`
Set spark major version
Available profiles are
```
-Pspark-2.0
-Pspark-1.6
-Pspark-1.5
-Pspark-1.4
-Pcassandra-spark-1.5
-Pcassandra-spark-1.4
-Pcassandra-spark-1.3
-Pcassandra-spark-1.2
-Pcassandra-spark-1.1
```
minor version can be adjusted by `-Dspark.version=x.x.x`
##### `-Phadoop-[version]`
set hadoop major version
Available profiles are
```
-Phadoop-0.23
-Phadoop-1
-Phadoop-2.2
-Phadoop-2.3
-Phadoop-2.4
-Phadoop-2.6
```
minor version can be adjusted by `-Dhadoop.version=x.x.x`
##### `-Pscala-[version] (optional)`
set scala version (default 2.10)
Available profiles are
```
-Pscala-2.10
-Pscala-2.11
```
##### `-Pyarn` (optional)
enable YARN support for local mode
> YARN for local mode is not supported for Spark v1.5.0 or higher. Set `SPARK_HOME` instead.
##### `-Ppyspark` (optional)
enable [PySpark](http://spark.apache.org/docs/latest/api/python/) support for local mode.
##### `-Pr` (optional)
enable [R](https://www.r-project.org/) support with [SparkR](https://spark.apache.org/docs/latest/sparkr.html) integration.
##### `-Psparkr` (optional)
another [R](https://www.r-project.org/) support with [SparkR](https://spark.apache.org/docs/latest/sparkr.html) integration as well as local mode support.
##### `-Pvendor-repo` (optional)
enable 3rd party vendor repository (cloudera)
##### `-Pmapr[version]` (optional)
For the MapR Hadoop Distribution, these profiles will handle the Hadoop version. As MapR allows different versions of Spark to be installed, you should specify which version of Spark is installed on the cluster by adding a Spark profile (`-Pspark-1.6`, `-Pspark-2.0`, etc.) as needed.
The correct Maven artifacts can be found for every version of MapR at http://doc.mapr.com
Available profiles are
```
-Pmapr3
-Pmapr40
-Pmapr41
-Pmapr50
-Pmapr51
```
#### -Pexamples (optional)
Bulid examples under zeppelin-examples directory
#### Example
Here're some examples:
```sh
# build with spark-2.0, scala-2.11
./dev/change_scala_version.sh 2.11
mvn clean package -Pspark-2.0 -Phadoop-2.4 -Pyarn -Ppyspark -Psparkr -Pscala-2.11
# build with spark-1.6, scala-2.10
mvn clean package -Pspark-1.6 -Phadoop-2.4 -Pyarn -Ppyspark -Psparkr
# spark-cassandra integration
mvn clean package -Pcassandra-spark-1.5 -Dhadoop.version=2.6.0 -Phadoop-2.6 -DskipTests
# with CDH
mvn clean package -Pspark-1.5 -Dhadoop.version=2.6.0-cdh5.5.0 -Phadoop-2.6 -Pvendor-repo -DskipTests
# with MapR
mvn clean package -Pspark-1.5 -Pmapr50 -DskipTests
```
#### Ignite Interpreter
```sh
mvn clean package -Dignite.version=1.6.0 -DskipTests
```
#### Scalding Interpreter
```sh
mvn clean package -Pscalding -DskipTests
```
### Configure
If you wish to configure Zeppelin option (like port number), configure the following files:
```
./conf/zeppelin-env.sh
./conf/zeppelin-site.xml
```
(You can copy `./conf/zeppelin-env.sh.template` into `./conf/zeppelin-env.sh`.
Same for `zeppelin-site.xml`.)
#### Setting SPARK_HOME and HADOOP_HOME
Without `SPARK_HOME` and `HADOOP_HOME`, Zeppelin uses embedded Spark and Hadoop binaries that you have specified with mvn build option.
If you want to use system provided Spark and Hadoop, export `SPARK_HOME` and `HADOOP_HOME` in `zeppelin-env.sh`.
You can use any supported version of spark without rebuilding Zeppelin.
```sh
# ./conf/zeppelin-env.sh
export SPARK_HOME=...
export HADOOP_HOME=...
```
#### External cluster configuration
Mesos
```sh
# ./conf/zeppelin-env.sh
export MASTER=mesos://...
export ZEPPELIN_JAVA_OPTS="-Dspark.executor.uri=/path/to/spark-*.tgz" or SPARK_HOME="/path/to/spark_home"
export MESOS_NATIVE_LIBRARY=/path/to/libmesos.so
```
If you set `SPARK_HOME`, you should deploy spark binary on the same location to all worker nodes. And if you set `spark.executor.uri`, every worker can read that file on its node.
Yarn
```sh
# ./conf/zeppelin-env.sh
export SPARK_HOME=/path/to/spark_dir
```
### Run
```sh
./bin/zeppelin-daemon.sh start
```
And browse [localhost:8080](localhost:8080) in your browser.
For configuration details check __`./conf`__ subdirectory.
### Building for Scala 2.11
To produce a Zeppelin package compiled with Scala 2.11, use the -Pscala-2.11 profile:
```
./dev/change_scala_version.sh 2.11
mvn clean package -Pspark-1.6 -Phadoop-2.4 -Pyarn -Ppyspark -Pscala-2.11 -DskipTests clean install
```
### Package
To package the final distribution including the compressed archive, run:
```sh
mvn clean package -Pbuild-distr
```
To build a distribution with specific profiles, run:
```sh
mvn clean package -Pbuild-distr -Pspark-1.5 -Phadoop-2.4 -Pyarn -Ppyspark
```
The profiles `-Pspark-1.5 -Phadoop-2.4 -Pyarn -Ppyspark` can be adjusted if you wish to build to a specific spark versions, or omit support such as `yarn`.
The archive is generated under _`zeppelin-distribution/target`_ directory
###Run end-to-end tests
Zeppelin comes with a set of end-to-end acceptance tests driving headless selenium browser
```sh
# assumes zeppelin-server running on localhost:8080 (use -Durl=.. to override)
mvn verify
# or take care of starting/stoping zeppelin-server from packaged zeppelin-distribuion/target
mvn verify -P using-packaged-distr
```
[![Analytics](https://ga-beacon.appspot.com/UA-45176241-4/apache/zeppelin/README.md?pixel)](https://github.com/igrigorik/ga-beacon)

View file

@ -33,6 +33,7 @@
<li role="separator" class="divider"></li>
<li class="title"><span><b>More</b><span></li>
<li><a href="{{BASE_PATH}}/install/upgrade.html">Upgrade Zeppelin Version</a></li>
<li><a href="{{BASE_PATH}}/install/build.html">Build from source</a></li>
<li><a href="{{BASE_PATH}}/quickstart/install_with_flink_and_spark_cluster.html">Install Zeppelin with Flink and Spark Clusters Tutorial</a></li>
</ul>
</li>
@ -100,8 +101,7 @@
<li><a href="{{BASE_PATH}}/rest-api/rest-credential.html">Credential API</a></li>
<li role="separator" class="divider"></li>
<li class="title"><span><b>Security</b><span></li>
<li><a href="{{BASE_PATH}}/security/authentication.html">Authentication for NGINX</a></li>
<li><a href="{{BASE_PATH}}/security/shiroauthentication.html">Shiro Authentication</a></li>
<li><a href="{{BASE_PATH}}/security/shiroauthentication.html">Shiro Authentication</a></li>
<li><a href="{{BASE_PATH}}/security/notebook_authorization.html">Notebook Authorization</a></li>
<li><a href="{{BASE_PATH}}/security/datasource_authorization.html">Data Source Authorization</a></li>
<li role="separator" class="divider"></li>

View file

@ -134,6 +134,7 @@ Join to our [Mailing list](https://zeppelin.apache.org/community.html) and repor
* [Customize Zeppelin Homepage](./manual/notebookashomepage.html) with one of your notebooks
* More
* [Upgrade Apache Zeppelin Version](./install/upgrade.html): a manual procedure of upgrading Apache Zeppelin version
* [Build](./install/build.html): Build from source
####Interpreter

343
docs/install/build.md Normal file
View file

@ -0,0 +1,343 @@
---
layout: page
title: "Build from Source"
description: "How to build Zeppelin from source"
group: install
---
<!--
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.
-->
{% include JB/setup %}
## Building from Source
<div id="toc"></div>
If you want to build from source, you must first install the following dependencies:
<table class="table-configuration">
<tr>
<th>Name</th>
<th>Value</th>
</tr>
<tr>
<td>Git</td>
<td>(Any Version)</td>
</tr>
<tr>
<td>Maven</td>
<td>3.1.x or higher</td>
</tr>
<tr>
<td>JDK</td>
<td>1.7</td>
</tr>
</table>
If you haven't installed Git and Maven yet, check the [Build requirements](#build-requirements) section and follow the step by step instructions from there.
####1. Clone the Apache Zeppelin repository
```
git clone https://github.com/apache/zeppelin.git
```
####2. Build source
You can build Zeppelin with following maven command:
```
mvn clean package -DskipTests [Options]
```
If you're unsure about the options, use the same commands that creates official binary package.
```bash
# update all pom.xml to use scala 2.11
./dev/change_scala_version.sh 2.11
# build zeppelin with all interpreters and include latest version of Apache spark support for local mode.
mvn clean package -DskipTests -Pspark-2.0 -Phadoop-2.4 -Pyarn -Ppyspark -Psparkr -Pr -Pscala-2.11
```
####3. Done
You can directly start Zeppelin by running after successful build:
```bash
./bin/zeppelin-daemon.sh start
```
Check [build-profiles](#build-profiles) section for further build options.
If you are behind proxy, follow instructions in [Proxy setting](#proxy-setting-optional) section.
If you're interested in contribution, please check [Contributing to Apache Zeppelin (Code)](../development/howtocontribute.html) and [Contributing to Apache Zeppelin (Website)](../../development/contributewebsite.html).
### Build profiles
#### Spark Interpreter
To build with a specific Spark version, Hadoop version or specific features, define one or more of the following profiles and options:
##### `-Pspark-[version]`
Set spark major version
Available profiles are
```
-Pspark-2.0
-Pspark-1.6
-Pspark-1.5
-Pspark-1.4
-Pcassandra-spark-1.5
-Pcassandra-spark-1.4
-Pcassandra-spark-1.3
-Pcassandra-spark-1.2
-Pcassandra-spark-1.1
```
minor version can be adjusted by `-Dspark.version=x.x.x`
##### `-Phadoop-[version]`
set hadoop major version
Available profiles are
```
-Phadoop-0.23
-Phadoop-1
-Phadoop-2.2
-Phadoop-2.3
-Phadoop-2.4
-Phadoop-2.6
```
minor version can be adjusted by `-Dhadoop.version=x.x.x`
##### `-Pscala-[version] (optional)`
set scala version (default 2.10)
Available profiles are
```
-Pscala-2.10
-Pscala-2.11
```
##### `-Pyarn` (optional)
enable YARN support for local mode
> YARN for local mode is not supported for Spark v1.5.0 or higher. Set `SPARK_HOME` instead.
##### `-Ppyspark` (optional)
enable [PySpark](http://spark.apache.org/docs/latest/api/python/) support for local mode.
##### `-Pr` (optional)
enable [R](https://www.r-project.org/) support with [SparkR](https://spark.apache.org/docs/latest/sparkr.html) integration.
##### `-Psparkr` (optional)
another [R](https://www.r-project.org/) support with [SparkR](https://spark.apache.org/docs/latest/sparkr.html) integration as well as local mode support.
##### `-Pvendor-repo` (optional)
enable 3rd party vendor repository (cloudera)
##### `-Pmapr[version]` (optional)
For the MapR Hadoop Distribution, these profiles will handle the Hadoop version. As MapR allows different versions of Spark to be installed, you should specify which version of Spark is installed on the cluster by adding a Spark profile (`-Pspark-1.6`, `-Pspark-2.0`, etc.) as needed.
The correct Maven artifacts can be found for every version of MapR at http://doc.mapr.com
Available profiles are
```
-Pmapr3
-Pmapr40
-Pmapr41
-Pmapr50
-Pmapr51
```
#### -Pexamples (optional)
Bulid examples under zeppelin-examples directory
### Build command examples
Here are some examples with several options:
```bash
# build with spark-2.0, scala-2.11
./dev/change_scala_version.sh 2.11
mvn clean package -Pspark-2.0 -Phadoop-2.4 -Pyarn -Ppyspark -Psparkr -Pscala-2.11 -DskipTests
# build with spark-1.6, scala-2.10
mvn clean package -Pspark-1.6 -Phadoop-2.4 -Pyarn -Ppyspark -Psparkr -DskipTests
# spark-cassandra integration
mvn clean package -Pcassandra-spark-1.5 -Dhadoop.version=2.6.0 -Phadoop-2.6 -DskipTests -DskipTests
# with CDH
mvn clean package -Pspark-1.5 -Dhadoop.version=2.6.0-cdh5.5.0 -Phadoop-2.6 -Pvendor-repo -DskipTests
# with MapR
mvn clean package -Pspark-1.5 -Pmapr50 -DskipTests
```
Ignite Interpreter
```bash
mvn clean package -Dignite.version=1.6.0 -DskipTests
```
Scalding Interpreter
```bash
mvn clean package -Pscalding -DskipTests
```
## Build requirements
### Install requirements
If you don't have requirements prepared, install it.
(The installation method may vary according to your environment, example is for Ubuntu.)
```
sudo apt-get update
sudo apt-get install git
sudo apt-get install openjdk-7-jdk
sudo apt-get install npm
sudo apt-get install libfontconfig
```
### Install maven
```
wget http://www.eu.apache.org/dist/maven/maven-3/3.3.9/binaries/apache-maven-3.3.9-bin.tar.gz
sudo tar -zxf apache-maven-3.3.9-bin.tar.gz -C /usr/local/
sudo ln -s /usr/local/apache-maven-3.3.9/bin/mvn /usr/local/bin/mvn
```
_Notes:_
- Ensure node is installed by running `node --version`
- Ensure maven is running version 3.1.x or higher with `mvn -version`
- Configure maven to use more memory than usual by `export MAVEN_OPTS="-Xmx2g -XX:MaxPermSize=1024m"`
## Proxy setting (optional)
If you're behind the proxy, you'll need to configure maven and npm to pass through it.
First of all, configure maven in your `~/.m2/settings.xml`.
```
<settings>
<proxies>
<proxy>
<id>proxy-http</id>
<active>true</active>
<protocol>http</protocol>
<host>localhost</host>
<port>3128</port>
<!-- <username>usr</username>
<password>pwd</password> -->
<nonProxyHosts>localhost|127.0.0.1</nonProxyHosts>
</proxy>
<proxy>
<id>proxy-https</id>
<active>true</active>
<protocol>https</protocol>
<host>localhost</host>
<port>3128</port>
<!-- <username>usr</username>
<password>pwd</password> -->
<nonProxyHosts>localhost|127.0.0.1</nonProxyHosts>
</proxy>
</proxies>
</settings>
```
Then, next commands will configure npm.
```
npm config set proxy http://localhost:3128
npm config set https-proxy http://localhost:3128
npm config set registry "http://registry.npmjs.org/"
npm config set strict-ssl false
```
Configure git as well
```
git config --global http.proxy http://localhost:3128
git config --global https.proxy http://localhost:3128
git config --global url."http://".insteadOf git://
```
To clean up, set `active false` in Maven `settings.xml` and run these commands.
```bash
npm config rm proxy
npm config rm https-proxy
git config --global --unset http.proxy
git config --global --unset https.proxy
git config --global --unset url."http://".insteadOf
```
_Notes:_
- If you are behind NTLM proxy you can use [Cntlm Authentication Proxy](http://cntlm.sourceforge.net/).
- Replace `localhost:3128` with the standard pattern `http://user:pwd@host:port`.
## Package
To package the final distribution including the compressed archive, run:
```sh
mvn clean package -Pbuild-distr
```
To build a distribution with specific profiles, run:
```sh
mvn clean package -Pbuild-distr -Pspark-1.5 -Phadoop-2.4 -Pyarn -Ppyspark
```
The profiles `-Pspark-1.5 -Phadoop-2.4 -Pyarn -Ppyspark` can be adjusted if you wish to build to a specific spark versions, or omit support such as `yarn`.
The archive is generated under _`zeppelin-distribution/target`_ directory
## Run end-to-end tests
Zeppelin comes with a set of end-to-end acceptance tests driving headless selenium browser
```sh
# assumes zeppelin-server running on localhost:8080 (use -Durl=.. to override)
mvn verify
# or take care of starting/stoping zeppelin-server from packaged zeppelin-distribuion/target
mvn verify -P using-packaged-distr
```
[![Analytics](https://ga-beacon.appspot.com/UA-45176241-4/apache/zeppelin/README.md?pixel)](https://github.com/igrigorik/ga-beacon)

View file

@ -44,86 +44,28 @@ Apache Zeppelin officially supports and is tested on the following environments:
</tr>
</table>
To install Apache Zeppelin, you have two options:
* You can [download pre-built binary packages](#downloading-binary-package) from the archive. This is usually easier than building from source, and you can download the latest stable version (or older versions, if necessary).
* You can also [build from source](#building-from-source). This gives you a development version of Zeppelin, which is more unstable but has new features.
### Downloading Binary Package
Stable binary packages are available on the [Apache Zeppelin Download Page](http://zeppelin.apache.org/download.html). You can download a default package with all interpreters, or you can download the *net-install* package, which lets you choose which interpreters to install.
Two binary packages are available on the [Apache Zeppelin Download Page](http://zeppelin.apache.org/download.html). Only difference between these two binaries is interpreters are included in the package file.
If you downloaded the default package, just unpack it in a directory of your choice and you're ready to go. If you downloaded the *net-install* package, you should manually [install additional interpreters](../manual/interpreterinstallation.html) first. You can also install everything by running `./bin/install-interpreter.sh --all`.
- #### Package with `all` interpreters.
After unpacking, jump to the [Starting Apache Zeppelin from Command Line](#starting-apache-zeppelin-from-the-command-line).
Just unpack it in a directory of your choice and you're ready to go.
### Building from Source
- #### Package with `net-install` interpreters.
If you want to build from source, you must first install the following dependencies:
<table class="table-configuration">
<tr>
<th>Name</th>
<th>Value</th>
</tr>
<tr>
<td>Git</td>
<td>(Any Version)</td>
</tr>
<tr>
<td>Maven</td>
<td>3.1.x or higher</td>
</tr>
</table>
If you haven't installed Git and Maven yet, check the [Before Build](https://github.com/apache/zeppelin/blob/master/README.md#before-build) section and follow the step by step instructions from there.
####1. Clone the Apache Zeppelin repository
```
git clone https://github.com/apache/zeppelin.git
```
####2. Build source with options
Each interpreter requires different build options. For more information about build options, please see the [Build](https://github.com/apache/zeppelin#build) section.
```
mvn clean package -DskipTests [Options]
```
Here are some examples with several options:
```
# build with spark-2.0, scala-2.11
./dev/change_scala_version.sh 2.11
mvn clean package -Pspark-2.0 -Phadoop-2.4 -Pyarn -Ppyspark -Psparkr -Pscala-2.11
# build with spark-1.6, scala-2.10
mvn clean package -Pspark-1.6 -Phadoop-2.4 -Pyarn -Ppyspark -Psparkr
# spark-cassandra integration
mvn clean package -Pcassandra-spark-1.5 -Dhadoop.version=2.6.0 -Phadoop-2.6 -DskipTests
# with CDH
mvn clean package -Pspark-1.5 -Dhadoop.version=2.6.0-cdh5.5.0 -Phadoop-2.6 -Pvendor-repo -DskipTests
# with MapR
mvn clean package -Pspark-1.5 -Pmapr50 -DskipTests
```
For further information about building from source, please see [README.md](https://github.com/apache/zeppelin/blob/master/README.md) in the Zeppelin repository.
Unpack and follow [install additional interpreters](../manual/interpreterinstallation.html) to install interpreters. If you're unsure, just run `./bin/install-interpreter.sh --all` and install all interpreters.
## Starting Apache Zeppelin from the Command Line
#### Starting Apache Zeppelin
On all platforms except for Windows:
On all unix like platforms:
```
bin/zeppelin-daemon.sh start
```
If you are using Windows:
If you are on Windows:
```
bin\zeppelin.cmd
@ -137,63 +79,36 @@ After Zeppelin has started successfully, go to [http://localhost:8080](http://lo
bin/zeppelin-daemon.sh stop
```
#### (Optional) Start Apache Zeppelin with a service manager
> **Note :** The below description was written based on Ubuntu Linux.
Apache Zeppelin can be auto-started as a service with an init script, using a service manager like **upstart**.
This is an example upstart script saved as `/etc/init/zeppelin.conf`
This allows the service to be managed with commands such as
```
sudo service zeppelin start
sudo service zeppelin stop
sudo service zeppelin restart
```
Other service managers could use a similar approach with the `upstart` argument passed to the `zeppelin-daemon.sh` script.
```
bin/zeppelin-daemon.sh upstart
```
**zeppelin.conf**
```
description "zeppelin"
start on (local-filesystems and net-device-up IFACE!=lo)
stop on shutdown
# Respawn the process on unexpected termination
respawn
# respawn the job up to 7 times within a 5 second period.
# If the job exceeds these values, it will be stopped and marked as failed.
respawn limit 7 5
# zeppelin was installed in /usr/share/zeppelin in this example
chdir /usr/share/zeppelin
exec bin/zeppelin-daemon.sh upstart
```
## Next Steps
Congratulations, you have successfully installed Apache Zeppelin! Here are two next steps you might find useful:
Congratulations, you have successfully installed Apache Zeppelin! Here are few steps you might find useful:
#### If you are new to Apache Zeppelin...
* For an in-depth overview of the Apache Zeppelin UI, head to [Explore Apache Zeppelin UI](../quickstart/explorezeppelinui.html).
* After getting familiar with the Apache Zeppelin UI, have fun with a short walk-through [Tutorial](../quickstart/tutorial.html) that uses the Apache Spark backend.
* If you need more configuration for Apache Zeppelin, jump to the next section: [Apache Zeppelin Configuration](#apache-zeppelin-configuration).
#### New to Apache Zeppelin...
* For an in-depth overview, head to [Explore Apache Zeppelin UI](../quickstart/explorezeppelinui.html).
* And then, try run [tutorial](http://localhost:8080/#/notebook/2A94M5J1Z) notebook in your Zeppelin.
* And see how to change [configurations](#apache-zeppelin-configuration) like port number, etc.
#### If you need more information about Spark or JDBC interpreter settings...
* Apache Zeppelin provides deep integration with [Apache Spark](http://spark.apache.org/). For more information, see [Spark Interpreter for Apache Zeppelin](../interpreter/spark.html).
* You can also use generic JDBC connections in Apache Zeppelin. Go to [Generic JDBC Interpreter for Apache Zeppelin](../interpreter/jdbc.html).
#### If you are in a multi-user environment...
* You can set permissions for your notebooks and secure data resource in a multi-user environment. Go to **More** -> **Security** section.
#### Zeppelin with Apache Spark ...
* To know more about deep integration with [Apache Spark](http://spark.apache.org/), check [Spark Interpreter](../interpreter/spark.html).
#### Zeppelin with JDBC data sources ...
* Check [JDBC Interpreter](../interpreter/jdbc.html) to know more about configure and uses multiple JDBC data sources.
#### Zeppelin with Python ...
* Check [Python interpreter](../interpreter/python.html) to know more about Matplotlib, Pandas integration.
#### Multi-user environment ...
* Turn on [authentication](../security/shiroauthentication.html).
* Manage your [notebook permission](../security/notebook_authorization.html).
* For more informations, go to **More** -> **Security** section.
#### Other useful informations ...
* Learn how [Display System](../displaysystem/basicdisplaysystem.html) works.
* Use [Service Manager](#start-apache-zeppelin-with-a-service-manager) to start Zeppelin.
* If you're using previous version please see [Upgrade Zeppelin version](./upgrade.html).
## Apache Zeppelin Configuration
You can configure Apache Zeppelin with either **environment variables** in `conf/zeppelin-env.sh` (`conf\zeppelin-env.cmd` for Windows) or **Java properties** in `conf/zeppelin-site.xml`. If both are defined, then the **environment variables** will take priority.
@ -416,3 +331,50 @@ You can configure Apache Zeppelin with either **environment variables** in `conf
<td>Size (in characters) of the maximum text message that can be received by websocket.</td>
</tr>
</table>
#### Start Apache Zeppelin with a service manager
> **Note :** The below description was written based on Ubuntu Linux.
Apache Zeppelin can be auto-started as a service with an init script, using a service manager like **upstart**.
This is an example upstart script saved as `/etc/init/zeppelin.conf`
This allows the service to be managed with commands such as
```
sudo service zeppelin start
sudo service zeppelin stop
sudo service zeppelin restart
```
Other service managers could use a similar approach with the `upstart` argument passed to the `zeppelin-daemon.sh` script.
```
bin/zeppelin-daemon.sh upstart
```
**zeppelin.conf**
```
description "zeppelin"
start on (local-filesystems and net-device-up IFACE!=lo)
stop on shutdown
# Respawn the process on unexpected termination
respawn
# respawn the job up to 7 times within a 5 second period.
# If the job exceeds these values, it will be stopped and marked as failed.
respawn limit 7 5
# zeppelin was installed in /usr/share/zeppelin in this example
chdir /usr/share/zeppelin
exec bin/zeppelin-daemon.sh upstart
```
## Building from Source
If you want to build from source instead of using binary package, follow the instructions [here](./build.html).

View file

@ -78,13 +78,6 @@ print (z.select("f1",[("o1","1"),("o2","2")],"2"))
print("".join(z.checkbox("f3", [("o1","1"), ("o2","2")],["1"])))
```
## Zeppelin features not fully supported by the Python Interpreter
* Interrupt a paragraph execution (`cancel()` method) is currently only supported in Linux and MacOs. If interpreter runs in another operating system (for instance MS Windows) , interrupt a paragraph will close the whole interpreter. A JIRA ticket ([ZEPPELIN-893](https://issues.apache.org/jira/browse/ZEPPELIN-893)) is opened to implement this feature in a next release of the interpreter.
* Progression bar in webUI (`getProgress()` method) is currently not implemented.
* Code-completion is currently not implemented.
## Matplotlib integration
The python interpreter can display matplotlib figures inline automatically using the `pyplot` module:
@ -166,3 +159,11 @@ Otherwise it can be referred to as `%python.sql`
## Technical description
For in-depth technical details on current implementation please refer to [python/README.md](https://github.com/apache/zeppelin/blob/master/python/README.md).
### Some features not yet implemented in the Python Interpreter
* Interrupt a paragraph execution (`cancel()` method) is currently only supported in Linux and MacOs. If interpreter runs in another operating system (for instance MS Windows) , interrupt a paragraph will close the whole interpreter. A JIRA ticket ([ZEPPELIN-893](https://issues.apache.org/jira/browse/ZEPPELIN-893)) is opened to implement this feature in a next release of the interpreter.
* Progression bar in webUI (`getProgress()` method) is currently not implemented.
* Code-completion is currently not implemented.

View file

@ -23,8 +23,7 @@ limitations under the License.
<div id="toc"></div>
There are multiple ways to enable authentication in Apache Zeppelin. This page describes HTTP basic auth using NGINX.
One option is to use [Basic Access Authentication](https://en.wikipedia.org/wiki/Basic_access_authentication).
[Build in authentication mechanism](./shiroauthentication.html) is recommended way for authentication. In case of you want authenticate using NGINX and [HTTP basic auth](https://en.wikipedia.org/wiki/Basic_access_authentication), please read this document.
## HTTP Basic Authentication using NGINX

View file

@ -33,22 +33,10 @@ You can setup **Zeppelin notebook authentication** in some simple steps.
### 1. Enable Shiro
By default in `conf`, you will find `shiro.ini.template`, this file is used as an example and it is strongly recommended
to create a `shiro.ini` file by doing the following command line `cp conf/shiro.ini.template conf/shiro.ini`.
to create a `shiro.ini` file by doing the following command line
### 2. Secure the HTTP channel
To secure the HTTP channel, you have to change both **anon** and **authc** settings in `conf/shiro.ini`. In here, **anon** means "the access is anonymous" and **authc** means "formed auth security".
The default status of them is
```
/** = anon
#/** = authc
```
Deactivate the line "/** = anon" and activate the line "/** = authc" in `conf/shiro.ini` file.
```
#/** = anon
/** = authc
```bash
cp conf/shiro.ini.template conf/shiro.ini
```
For the further information about `shiro.ini` file format, please refer to [Shiro Configuration](http://shiro.apache.org/configuration.html#Configuration-INISections).
@ -193,3 +181,9 @@ If you want to grant this permission to other users, you can change **roles[ ]**
<br/>
> **NOTE :** All of the above configurations are defined in the `conf/shiro.ini` file. This documentation is originally from [SECURITY-README.md](https://github.com/apache/zeppelin/blob/master/SECURITY-README.md).
## Other authentication methods
- [HTTP Basic Authentication using NGINX](./authentication.html)

View file

@ -119,6 +119,7 @@ class PyZeppelinContext(object):
def __init__(self):
self.max_result = 1000
self._displayhook = lambda *args: None
self._setup_matplotlib()
def input(self, name, defaultValue=""):
print(self.errorMsg)
@ -206,7 +207,7 @@ class PyZeppelinContext(object):
try:
import matplotlib
except ImportError:
pass
return
# Make sure custom backends are available in the PYTHONPATH
rootdir = os.environ.get('ZEPPELIN_HOME', os.getcwd())
mpl_path = os.path.join(rootdir, 'interpreter', 'lib', 'python')
@ -217,7 +218,7 @@ class PyZeppelinContext(object):
try:
matplotlib.use('module://backend_zinline')
import backend_zinline
# Everything looks good so make config assuming that we are using
# an inline backend
self._displayhook = backend_zinline.displayhook
@ -231,4 +232,3 @@ class PyZeppelinContext(object):
z = PyZeppelinContext()
z._setup_matplotlib()

View file

@ -26,6 +26,7 @@ class Py4jZeppelinContext(PyZeppelinContext):
"""A context impl that uses Py4j to communicate to JVM
"""
def __init__(self, z):
PyZeppelinContext.__init__(self)
self.z = z
self.paramOption = gateway.jvm.org.apache.zeppelin.display.Input.ParamOption
self.javaList = gateway.jvm.java.util.ArrayList

View file

@ -437,13 +437,13 @@ public class PySparkInterpreter extends Interpreter implements ExecuteResultHand
statementSetNotifier.notify();
}
String[] completionList = null;
synchronized (statementFinishedNotifier) {
long startTime = System.currentTimeMillis();
while (statementOutput == null
&& pythonScriptInitialized == false
&& pythonscriptRunning) {
try {
if (System.currentTimeMillis() - startTime < MAX_TIMEOUT_SEC * 1000) {
if (System.currentTimeMillis() - startTime > MAX_TIMEOUT_SEC * 1000) {
logger.error("pyspark completion didn't have response for {}sec.", MAX_TIMEOUT_SEC);
break;
}
@ -454,16 +454,20 @@ public class PySparkInterpreter extends Interpreter implements ExecuteResultHand
return new LinkedList<>();
}
}
if (statementError) {
return new LinkedList<>();
}
InterpreterResult completionResult;
completionResult = new InterpreterResult(Code.SUCCESS, statementOutput);
Gson gson = new Gson();
completionList = gson.fromJson(completionResult.message(), String[].class);
}
if (statementError) {
return new LinkedList<>();
}
InterpreterResult completionResult = new InterpreterResult(Code.SUCCESS, statementOutput);
//end code for completion
Gson gson = new Gson();
String[] completionList = gson.fromJson(completionResult.message(), String[].class);
if (completionList == null) {
return new LinkedList<>();
}
List<InterpreterCompletion> results = new LinkedList<>();
for (String name: completionList) {
results.add(new InterpreterCompletion(name, name));

View file

@ -25,6 +25,7 @@ import org.apache.zeppelin.interpreter.InterpreterGroup;
import org.apache.zeppelin.interpreter.InterpreterOutputListener;
import org.apache.zeppelin.interpreter.InterpreterOutput;
import org.apache.zeppelin.interpreter.InterpreterResult;
import org.apache.zeppelin.interpreter.thrift.InterpreterCompletion;
import org.apache.zeppelin.resource.LocalResourcePool;
import org.apache.zeppelin.user.AuthenticationInfo;
import org.junit.After;
@ -37,6 +38,7 @@ import org.slf4j.LoggerFactory;
import java.io.File;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Properties;
import static org.junit.Assert.*;
@ -144,4 +146,11 @@ public class PySparkInterpreterTest {
}
}
@Test
public void testCompletion() {
if (getSparkVersionNumber() > 11) {
List<InterpreterCompletion> completions = pySparkInterpreter.completion("sc.", "sc.".length());
assertTrue(completions.size() > 0);
}
}
}

View file

@ -48,13 +48,7 @@ import org.apache.zeppelin.interpreter.InterpreterSetting;
import org.apache.zeppelin.interpreter.remote.RemoteAngularObjectRegistry;
import org.apache.zeppelin.interpreter.remote.RemoteInterpreterProcessListener;
import org.apache.zeppelin.interpreter.thrift.InterpreterCompletion;
import org.apache.zeppelin.notebook.JobListenerFactory;
import org.apache.zeppelin.notebook.Note;
import org.apache.zeppelin.notebook.Notebook;
import org.apache.zeppelin.notebook.NotebookAuthorization;
import org.apache.zeppelin.notebook.NotebookEventListener;
import org.apache.zeppelin.notebook.Paragraph;
import org.apache.zeppelin.notebook.ParagraphJobListener;
import org.apache.zeppelin.notebook.*;
import org.apache.zeppelin.notebook.repo.NotebookRepo.Revision;
import org.apache.zeppelin.notebook.socket.Message;
import org.apache.zeppelin.notebook.socket.Message.OP;
@ -234,6 +228,9 @@ public class NotebookServer extends WebSocketServlet implements
case NOTE_UPDATE:
updateNote(conn, userAndRoles, notebook, messagereceived);
break;
case NOTE_RENAME:
renameNote(conn, userAndRoles, notebook, messagereceived);
break;
case COMPLETION:
completion(conn, userAndRoles, notebook, messagereceived);
break;
@ -701,6 +698,34 @@ public class NotebookServer extends WebSocketServlet implements
}
}
private void renameNote(NotebookSocket conn, HashSet<String> userAndRoles,
Notebook notebook, Message fromMessage)
throws SchedulerException, IOException {
String noteId = (String) fromMessage.get("id");
String name = (String) fromMessage.get("name");
if (noteId == null) {
return;
}
NotebookAuthorization notebookAuthorization = notebook.getNotebookAuthorization();
if (!notebookAuthorization.isOwner(noteId, userAndRoles)) {
permissionError(conn, "renameNote", fromMessage.principal,
userAndRoles, notebookAuthorization.getOwners(noteId));
return;
}
Note note = notebook.getNote(noteId);
if (note != null) {
note.setName(name);
AuthenticationInfo subject = new AuthenticationInfo(fromMessage.principal);
note.persist(subject);
broadcastNote(note);
broadcastNoteList(subject, userAndRoles);
}
}
private boolean isCronUpdated(Map<String, Object> configA,
Map<String, Object> configB) {
boolean cronUpdated = false;

View file

@ -88,6 +88,10 @@
}
});
$scope.renameNote = function(node) {
noteActionSrv.renameNote(node.id, node.path);
};
$scope.removeNote = function(noteId) {
noteActionSrv.removeNote(noteId, false);
};

View file

@ -14,20 +14,26 @@ limitations under the License.
<script type="text/ng-template" id="notebook_folder_renderer.html">
<div ng-if="node.children == null"
ng-mouseenter="showButton=true"
ng-mouseleave="showButton=false">
ng-mouseenter="showNoteButton=true"
ng-mouseleave="showNoteButton=false">
<a style="text-decoration: none;" href="#/notebook/{{node.id}}">
<i style="font-size: 10px;" class="icon-doc"/> {{noteName(node)}}
</a>
<a style="text-decoration: none;">
<i style="font-size: 13px; margin-left: 10px; cursor: pointer; text-decoration: none;"
class="fa fa-eraser" ng-show="showButton" ng-click="clearAllParagraphOutput(node.id)"
class="fa fa-pencil" ng-show="showNoteButton" ng-click="renameNote(node)"
tooltip-placement="bottom" tooltip="Rename note">
</i>
</a>
<a style="text-decoration: none;">
<i style="font-size: 13px; margin-left: 2px; cursor: pointer; text-decoration: none;"
class="fa fa-eraser" ng-show="showNoteButton" ng-click="clearAllParagraphOutput(node.id)"
tooltip-placement="bottom" tooltip="Clear output">
</i>
</a>
<a style="text-decoration: none;">
<i style="font-size: 13px; margin-left: 2px; cursor: pointer; text-decoration: none;"
class="fa fa-trash-o" ng-show="showButton" ng-click="removeNote(node.id)"
class="fa fa-trash-o" ng-show="showNoteButton" ng-click="removeNote(node.id)"
tooltip-placement="bottom" tooltip="Remove note">
</i>
</a>

View file

@ -16,9 +16,9 @@
angular.module('zeppelinWebApp').service('noteActionSrv', noteActionSrv);
noteActionSrv.$inject = ['websocketMsgSrv', '$location'];
noteActionSrv.$inject = ['websocketMsgSrv', '$location', 'renameSrv'];
function noteActionSrv(websocketMsgSrv, $location) {
function noteActionSrv(websocketMsgSrv, $location, renameSrv) {
this.removeNote = function(noteId, redirectToHome) {
BootstrapDialog.confirm({
closable: true,
@ -47,5 +47,15 @@
}
});
};
this.renameNote = function(noteId, notePath) {
renameSrv.openRenameModal({
title: 'Rename note',
oldName: notePath,
callback: function(newName) {
websocketMsgSrv.renameNote(noteId, newName);
}
});
};
}
})();

View file

@ -43,7 +43,8 @@
if (nodes.length === 1) { // the leaf
curDir.children.push({
name: nodes[0],
id: noteId
id: noteId,
path: curDir.id ? curDir.id + '/' + nodes[0] : nodes[0]
});
} else { // a folder node
var node = nodes.shift();
@ -53,6 +54,7 @@
addNode(dir, nodes, noteId);
} else {
var newDir = {
id: curDir.id ? curDir.id + '/' + node : node,
name: node,
hidden: true,
children: []

View file

@ -0,0 +1,50 @@
/*
* 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.
*/
'use strict';
(function() {
angular.module('zeppelinWebApp').controller('RenameCtrl', RenameCtrl);
RenameCtrl.$inject = ['$scope'];
function RenameCtrl($scope) {
var self = this;
$scope.params = {newName: ''};
$scope.isValid = true;
$scope.rename = function() {
angular.element('#renameModal').modal('hide');
self.callback($scope.params.newName);
};
$scope.$on('openRenameModal', function(event, options) {
self.validator = options.validator || defaultValidator;
self.callback = options.callback || function() {};
$scope.title = options.title || 'Rename';
$scope.params.newName = options.oldName || '';
$scope.validate = function() {
$scope.isValid = self.validator($scope.params.newName);
};
angular.element('#renameModal').modal('show');
});
function defaultValidator(str) {
return !!str.trim();
}
}
})();

View file

@ -0,0 +1,42 @@
<!--
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.
-->
<div id="renameModal" class="modal fade" role="dialog"
tabindex="-1">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal">&times;</button>
<h4 class="modal-title">{{title}}</h4>
</div>
<div class="modal-body">
<label ng-if="isValid">Please enter a new name</label>
<label class="text-danger" ng-if="!isValid">Please enter a valid name</label>
<div class="form-group" ng-class="{'has-error': !isValid}">
<input type="text" class="form-control"
ng-model="params.newName" ng-change="validate()"
ng-keyup="$event.keyCode == 13 && isValid && rename()" />
</div>
</div>
<div class="modal-footer">
<div>
<button type="button" class="btn btn-default btn-primary"
ng-click="rename()" ng-class="{'disabled': !isValid}">
Rename
</button>
</div>
</div>
</div>
</div>
</div>

View file

@ -0,0 +1,35 @@
/*
* 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.
*/
'use strict';
(function() {
angular.module('zeppelinWebApp').service('renameSrv', renameSrv);
renameSrv.$inject = ['$rootScope'];
function renameSrv($rootScope) {
var self = this;
/**
* <options schema>
* title: string - Modal title
* oldName: string - name to initialize input
* callback: (newName: string)=>void - callback onButtonClick
* validator: (str: string)=>boolean - input validator
*/
self.openRenameModal = function(options) {
$rootScope.$broadcast('openRenameModal', options);
};
}
})();

View file

@ -59,6 +59,10 @@
websocketEvents.sendNewEvent({op: 'NOTE_UPDATE', data: {id: noteId, name: noteName, config: noteConfig}});
},
renameNote: function(noteId, noteName) {
websocketEvents.sendNewEvent({op: 'NOTE_RENAME', data: {id: noteId, name: noteName}});
},
moveParagraph: function(paragraphId, newIndex) {
websocketEvents.sendNewEvent({op: 'MOVE_PARAGRAPH', data: {id: paragraphId, index: newIndex}});
},

View file

@ -93,6 +93,9 @@ limitations under the License.
<div ng-controller="LoginCtrl as noteimportctrl">
<div id="login-container" ng-include src="'components/login/login.html'"></div>
</div>
<div ng-controller="RenameCtrl">
<div ng-include src="'components/rename/rename.html'"></div>
</div>
<!-- build:js(.) scripts/oldieshim.js -->
<!--[if lt IE 9]>
<script src="bower_components/es5-shim/es5-shim.js"></script>
@ -212,6 +215,8 @@ limitations under the License.
<script src="components/login/login.controller.js"></script>
<script src="components/elasticInputCtrl/elasticInput.controller.js"></script>
<script src="components/noteAction/noteAction.service.js"></script>
<script src="components/rename/rename.controller.js"></script>
<script src="components/rename/rename.service.js"></script>
<!-- endbuild -->
</body>
</html>

View file

@ -46,7 +46,7 @@ describe('Factory: NoteList', function() {
expect(folderList[1].name).toBe('B');
expect(folderList[2].name).toBe('000003');
expect(folderList[3].name).toBe('C');
expect(folderList[3].id).toBeUndefined();
expect(folderList[3].id).toBe('C');
expect(folderList[3].children.length).toBe(3);
expect(folderList[3].children[0].name).toBe('CA');
expect(folderList[3].children[0].id).toBe('000004');
@ -55,7 +55,7 @@ describe('Factory: NoteList', function() {
expect(folderList[3].children[1].id).toBe('000005');
expect(folderList[3].children[1].children).toBeUndefined();
expect(folderList[3].children[2].name).toBe('CB');
expect(folderList[3].children[2].id).toBeUndefined();
expect(folderList[3].children[2].id).toBe('C/CB');
expect(folderList[3].children[2].children.length).toBe(3);
expect(folderList[3].children[2].children[0].name).toBe('CBA');
expect(folderList[3].children[2].children[0].id).toBe('000006');
@ -67,10 +67,10 @@ describe('Factory: NoteList', function() {
expect(folderList[3].children[2].children[2].id).toBe('000008');
expect(folderList[3].children[2].children[2].children).toBeUndefined();
expect(folderList[4].name).toBe('D');
expect(folderList[4].id).toBeUndefined();
expect(folderList[4].id).toBe('D');
expect(folderList[4].children.length).toBe(1);
expect(folderList[4].children[0].name).toBe('D[A');
expect(folderList[4].children[0].id).toBeUndefined();
expect(folderList[4].children[0].id).toBe('D/D[A');
expect(folderList[4].children[0].children[0].name).toBe('DA]B');
expect(folderList[4].children[0].children[0].id).toBe('000009');
expect(folderList[4].children[0].children[0].children).toBeUndefined();

View file

@ -53,6 +53,8 @@ public class Message {
// @param object notebook
NOTE_UPDATE,
NOTE_RENAME,
RUN_PARAGRAPH, // [c-s] run paragraph
// @param id paragraph id
// @param paragraph paragraph content.ie. script