Ubuntu 22.04 安装 Apache Jackrabbit 2.22.5 指南
在 Ubuntu 22.04 上从零安装 Apache Jackrabbit 2.22.5(standalone 可执行 jar),实测配置 JDK 17/JAVA_HOME、修正 persistence 配置、启动 8080 服务并通过 WebDAV 与 JCR API 创建 workspace 与内容节点。
Ubuntu 22.04 安装 Apache Jackrabbit 2.22.5 指南
目标:在 Ubuntu 22.04 上从 0 到 1 完整部署 Apache Jackrabbit 2.22.5(JSR-283/JSR-333 JCR 内容仓库的 Java 实现),开通 8080 端口的 HTTP 服务,并在 WebDAV 与 JCR 客户端里实测创建 workspace 与内容节点。全部命令与回显均在真实 Ubuntu 22.04.5 LTS 环境实测通过(JDK 17,路径
/opt/apache-jackrabbit/、/opt/data/jackrabbit/)。
一、环境信息
- 操作系统:Ubuntu 22.04.5 LTS(Linux x86_64)
- JDK:OpenJDK
17.0.20.1(java-17-openjdk-amd64),JAVA_HOME=/usr/lib/jvm/java-17-openjdk-amd64 - Apache Jackrabbit:
2.22.5(standalone 版jackrabbit-standalone-2.22.5.jar,Java 可执行 jar) - 服务监听:HTTP
0.0.0.0:8080 - 安装目录:
/opt/apache-jackrabbit/ - 仓库数据目录:
/opt/data/jackrabbit/ - 仓库配置文件:
/opt/apache-jackrabbit/conf/repository.xml(实测改名为repository-fs.xml使用文件持久化) - HTTP 端点:
/server/*(JCR Remoting,即 davE)、/repository/*(WebDAV) - 演示管理账号:
admin/q1w2e3r4
⚠️ 注意:Apache Jackrabbit 与 Apache Jackrabbit Oak(
jackrabbit-oak)是两个独立发行线。本文只讲经典 Jackrabbit 核心(jackrabbit-core,2.x standalone);Oak 属下一代内容仓库实现,见「三、版本选型说明」。
二、前置条件
- Ubuntu 22.04 真机,具备 root 权限,可访问外网(需从
downloads.apache.org/archive.apache.org下载软件包)。 - 服务器尚未安装 JDK。先更新软件源并安装 JDK 17:
# 使用 root 或 sudo 执行
apt-get update
# 安装 OpenJDK 17(Jackrabbit 2.22.x 官方以 JDK 8/11/17 构建,此处用 17)
apt-get install -y openjdk-17-jdk-headless
- 校验 Java 版本:
java -version
实测回显如下:
openjdk version "17.0.20.1" 2026-08-18
OpenJDK Runtime Environment (build 17.0.20.1+1-1-22.04-Ubuntu)
OpenJDK 64-Bit Server VM (build 17.0.20.1+1-1-22.04-Ubuntu, mixed mode, sharing)
- 定位 JDK 安装路径并写入环境变量(standalone jar 通过
java -jar运行,JAVA_HOME供定义 JDK 路径使用)。自动探测路径:
JAVA_HOME=$(dirname $(dirname $(readlink -f $(which java))))
echo "JAVA_HOME=$JAVA_HOME"
实测回显:
JAVA_HOME=/usr/lib/jvm/java-17-openjdk-amd64
如需持久化,追加到 /etc/environment:
echo 'JAVA_HOME=/usr/lib/jvm/java-17-openjdk-amd64' >> /etc/environment
echo 'PATH=/usr/lib/jvm/java-17-openjdk-amd64/bin:$PATH' >> /etc/profile.d/java.sh
WebDAV 客户端测试依赖 curl 与解压工具(可选):
apt-get install -y curl unzip
💡 说明:本指南下载使用
curl,若偏好wget可先apt-get install -y wget后再用wget <同 URL>命令,二者等效。
三、版本选型说明
3.1 两个发行线的选择
Apache Jackrabbit 生态有两条主线,部署前务必区分:
| 主线 | 组件坐标 | GAV 坐标 | 场景 |
|---|---|---|---|
| 经典 Jackrabbit | jackrabbit-core / jackrabbit-standalone | org.apache.jackrabbit:jackrabbit-standalone | JCR 1.0/2.0 规范的标准实现,轻量、单仓库,适合作为进程内内容仓库或独立 HTTP 服务 |
| Jackrabbit Oak | apache-jackrabbit-oak | org.apache.jackrabbit:oak-* | 下一代内容仓库,面向大规模/集群/高并发场景,是 Adobe Experience Manager(AEM) 的存储层,部署方式是打进应用/独立服务 |
本系列安装指南使用经典 Jackrabbit 2.x standalone。它和你可能听过的「Oak」不是同一个东西,不要混用配置与 jar。
3.2 版本获取方法
到 Apache 官方发行目录查看当前最新稳定版:
https://downloads.apache.org/jackrabbit/
实测列出的 2.x 发行版有 2.20.18/、2.22.5/(当前稳定版)、2.23.6-beta/(预发布),及 oak/(下一代 Oak 的家长目录)。本文以稳定版 2.22.5 为例。2.20 起 standalone 文件命名去掉了 apache- 前缀,即 jackrabbit-standalone-<ver>.jar。
四、下载与目录规划
创建目录并下载官方 standalone jar:
mkdir -p /opt/apache-jackrabbit
cd /opt/apache-jackrabbit
curl -fsSL -o jackrabbit-standalone-2.22.5.jar \
https://downloads.apache.org/jackrabbit/2.22.5/jackrabbit-standalone-2.22.5.jar
ls -la jackrabbit-standalone-2.22.5.jar
实测回显:
-rw-r--r-- 1 root root 104497574 Oct 11 11:09 jackrabbit-standalone-2.22.5.jar
校验文件完整性(SHA-512,对 jackrabbit-standalone-2.22.5.jar):
sha512sum jackrabbit-standalone-2.22.5.jar
实测回显:
89836e498555b7d9378ed6df1c2d5a7cf1765b5c6972eaf8098886465af46536f20715cc2877e355c9498ac341e1d2102840a07e538822a42280a376334e149a jackrabbit-standalone-2.22.5.jar
确认它是可执行 jar(Main-Class 为 org.apache.jackrabbit.standalone.Main):
unzip -p jackrabbit-standalone-2.22.5.jar META-INF/MANIFEST.MF | grep -i main-class
实测回显:
Main-Class: org.apache.jackrabbit.standalone.Main
准备仓库数据目录:
mkdir -p /opt/data/jackrabbit
五、部署步骤
5.1 抽取仓库配置文件(repository.xml)
standalone jar 内置默认 repository.xml,先抽取到 conf/ 目录以便后续配置:
cd /opt/apache-jackrabbit
mkdir -p conf
unzip -o jackrabbit-standalone-2.22.5.jar \
org/apache/jackrabbit/core/repository.xml -d conf/
mv conf/org/apache/jackrabbit/core/repository.xml conf/repository.xml
rm -rf conf/org
ls -la conf/
5.2 修正 persistence 配置(关键)
⚠️ 首次直接用默认配置启动会失败:默认
repository.xml的 workspace 与 version 均使用DerbyPersistenceManager(内嵌 Apache Derby JDBC 库),而jackrabbit-standalone-2.22.5.jar并没有把 Derby 驱动打进 fat jar,启动时会报:
javax.jcr.RepositoryException: Could not load JDBC driver class org.apache.derby.jdbc.EmbeddedDriver
...
Caused by: java.lang.ClassNotFoundException: org.apache.derby.jdbc.EmbeddedDriver
解决办法:把两处
DerbyPersistenceManager换成基于文件系统的BundleFsPersistenceManager(纯磁盘存储,无需任何 JDBC 驱动),并删掉只对 Derby 生效的url/schemaObjectPrefix参数。生成新配置conf/repository-fs.xml:
cd /opt/apache-jackrabbit/conf
cp repository.xml repository-fs.xml
# 两处(workspace persistence + version persistence)统一替换
sed -i \
's|org.apache.jackrabbit.core.persistence.pool.DerbyPersistenceManager|org.apache.jackrabbit.core.persistence.bundle.BundleFsPersistenceManager|g' \
repository-fs.xml
# 删除 Derby 专属参数
sed -i '/<param name="url" value="jdbc:derby:/d' repository-fs.xml
sed -i '/<param name="schemaObjectPrefix" value=/d' repository-fs.xml
校验改动(应只剩两处 PersistenceManager 类名变更为 BundleFsPersistenceManager,且不再有 Derby/build 字样):
diff repository.xml repository-fs.xml
核心差异(节选):
99,101c99
< <PersistenceManager class="org.apache.jackrabbit.core.persistence.pool.DerbyPersistenceManager">
< <param name="url" value="jdbc:derby:${wsp.home}/db;create=true"/>
< <param name="schemaObjectPrefix" value="${wsp.name}_"/>
---
> <PersistenceManager class="org.apache.jackrabbit.core.persistence.bundle.BundleFsPersistenceManager">
5.3 启动 Jackrabbit 服务
💡 先看 standalone 的完整用法:
java -jar jackrabbit-standalone-2.22.5.jar --help
usage: java -jar jackrabbit-standalone-2.22.5.jar [-?] [-b] [-c <arg>] [-C
<arg>] [-d] [-f <arg>] [-h <arg>] [-i <arg>] [-l] [-n] [-p <arg>]
[-q] [-r <arg>] [-R <arg>]
-?,--help print this message
-b,--backup create a backup of the repository
-c,--conf <arg> repository configuration file
-C,--backup-conf <arg> backup repository configuration file
-d,--debug enable debug logging
-f,--file <arg> location of this jar file
-h,--host <arg> IP address of the HTTP server
-i,--cli <arg> command line access to a remote repository
-l,--license print license information
-n,--notice print copyright notices
-p,--port <arg> TCP port of the HTTP server (8080)
-q,--quiet disable console output
-r,--repo <arg> repository directory (jackrabbit)
-R,--backup-repo <arg> backup repository directory (jackrabbit-backupN)
常用启动参数:-c 指定 repository.xml、-r 指定仓库数据目录、-p 端口(默认 8080)、-h 绑定地址。
前台直接启动(便于观察,Ctrl+C 停止):
cd /opt/apache-jackrabbit
JAVA_HOME=/usr/lib/jvm/java-17-openjdk-amd64
$JAVA_HOME/bin/java -jar jackrabbit-standalone-2.22.5.jar \
-c /opt/apache-jackrabbit/conf/repository-fs.xml \
-r /opt/data/jackrabbit
后台启动并把日志写入 /tmp/jr.log:
cd /opt/apache-jackrabbit
nohup $JAVA_HOME/bin/java -jar jackrabbit-standalone-2.22.5.jar \
-c /opt/apache-jackrabbit/conf/repository-fs.xml \
-r /opt/data/jackrabbit > /tmp/jr.log 2>&1 &
启动日志(实测回显):
Using repository directory /opt/data/jackrabbit
Writing log messages to /opt/data/jackrabbit/log
Welcome to Apache Jackrabbit!
-------------------------------
Starting the server...
Apache Jackrabbit is now running at http://localhost:8080/
运行级日志在 /opt/data/jackrabbit/log/jackrabbit.log(含各 servlet 初始化、Started ServerConnector ... 0.0.0.0:8080)。首次启动会自动创建 repository/、workspaces/、version/、tmp/、log/ 等目录。
5.4 验证服务与端点
# 仓库概览(davE 端点,列出所有 workspace,即本版本的「管理台」入口)
curl -s -u admin:q1w2e3r4 http://localhost:8080/server/
实测回显(工作区含默认自带两个 + 后续新建的 ws_demo):
<html><head><title>Jackrabbit 2.22.5</title></head><body><h2>Jackrabbit
2.22.5</h2><h3>Available Workspace Resources:</h3><ul><li><a
href="http://localhost:8080/server/default/">default</a></li><li><a
href="http://localhost:8080/server/security/">security</a></li><li><a
href="http://localhost:8080/server/ws_demo/">ws_demo</a></li></ul>
<hr size="1"><em>Powered by <a
href="http://jackrabbit.apache.org/">Jackrabbit</a> 2.22.5</em></body></html>
默认监听端口回显(访问日志 access.log.<日期>):
127.0.0.1 - - [11/Oct/2026:11:14:37 +0000] "PROPFIND /repository/default/ HTTP/1.1" 207 1505 "-" "curl/7.81.0"
5.5 实测创建 workspace 与内容节点
Jackrabbit 内容节点可通过 WebDAV(/repository/*)或 JCR API 创建;workspace 通过 JCR Workspace.createWorkspace() 创建。
A. WebDAV 创建内容节点
创建存放文件记录的集合(MKCOL):
curl -i -X MKCOL -u admin:q1w2e3r4 \
http://localhost:8080/repository/default/mydocs
实测回显:
HTTP/1.1 201 Created
Date: Sun, 11 Oct 2026 11:14:42 GMT
Content-Length: 0
向集合写入一个文本资源(PUT,等价创建 nt:file + nt:resource 节点):
curl -i -X PUT -u admin:q1w2e3r4 -H "Content-Type: text/plain" \
--data "Hello Jackrabbit!" \
http://localhost:8080/repository/default/mydocs/hello.txt
实测回显:
HTTP/1.1 201 Created
Date: Sun, 11 Oct 2026 11:14:42 GMT
Content-Length: 0
读回该资源内容:
curl -s -u admin:q1w2e3r4 \
http://localhost:8080/repository/default/mydocs/hello.txt
实测回显:
Hello Jackrabbit!
列出集合内子资源(PROPFIND,Depth 1):
curl -s -X PROPFIND -H "Depth: 1" -u admin:q1w2e3r4 \
http://localhost:8080/repository/default/mydocs/ > /tmp/pf.xml
grep -E "href>|displayname" /tmp/pf.xml | head
实测回显中可见 mydocs 与 hello.txt 两个资源。
B. JCR API 创建 workspace 与带属性节点
写一个小 Java 客户端(基于 standalone jar,内含完整 JCR 库),登录 admin,创建新 workspace ws_demo,并在 default workspace 根下加一个 nt:unstructured 节点 /api(含 author、version 两个属性):
import javax.jcr.*;
import java.util.Arrays;
import org.apache.jackrabbit.core.RepositoryImpl;
import org.apache.jackrabbit.core.config.RepositoryConfig;
public class JcrOps {
public static void main(String[] args) throws Exception {
RepositoryConfig config = RepositoryConfig.create(
"/opt/apache-jackrabbit/conf/repository-fs.xml", "/opt/data/jackrabbit");
RepositoryImpl repo = RepositoryImpl.create(config);
Session session = repo.login(
new SimpleCredentials("admin", "q1w2e3r4".toCharArray()), "default");
Workspace ws = session.getWorkspace();
if (!Arrays.asList(ws.getAccessibleWorkspaceNames()).contains("ws_demo")) {
ws.createWorkspace("ws_demo"); // 创建新 workspace
System.out.println("CREATED_WORKSPACE name=ws_demo");
}
Node api = session.getRootNode().addNode("api", "nt:unstructured");
api.setProperty("author", "tester");
api.setProperty("version", "1.2");
session.save();
System.out.println("CREATED_NODE path=" + api.getPath()
+ " primaryType=" + api.getPrimaryNodeType().getName());
System.out.println("== workspace list ==");
for (String name : ws.getAccessibleWorkspaceNames()) System.out.println(" " + name);
session.logout();
repo.shutdown();
}
}
编译并运行(需在 Jackrabbit 服务停止时执行,避免仓库目录锁冲突):
cd /opt/apache-jackrabbit
$JAVA_HOME/bin/javac -cp jackrabbit-standalone-2.22.5.jar JcrOps.java
$JAVA_HOME/bin/java -cp jackrabbit-standalone-2.22.5.jar:. JcrOps
实测回显:
== workspace list before ==
security
default
CREATED_WORKSPACE name=ws_demo
CREATED_NODE path=/api primaryType=nt:unstructured
== workspace list after ==
security
default
ws_demo
重启服务后可在 http://localhost:8080/server/ 看到 ws_demo,且 default 的 WebDAV PROPFIND 也能列出 /api 的 author、version 属性(见 5.4)。
C. davE(REST)读取节点
读取 default 工作区根节点(jcr:root,XML):
curl -s -u admin:q1w2e3r4 -H "Accept: application/json" \
http://localhost:8080/server/default/jcr%3aroot/
实测回显(节选,根为 rep:root,带 rep:AccessControllable mixin):
<?xml version="1.0" encoding="UTF-8"?><sv:node sv:name="jcr:root"
...><sv:property sv:name="jcr:primaryType" sv:type="Name"><sv:value>rep:root</sv:value>
</sv:property></sv:node>
⚠️ 注意:davE 对任意节点路径的 URL 采用
jcr:root为根的规范(/server/<workspace>/jcr:root/<路径>)。直接/server/default/api这种省略jcr:root的写法会返回 500(Unexpected format of resource path)。写内容节点优先用 WebDAV 的MKCOL/PUT,跨 workspace 管理用 JCR API。
六、配置说明
6.1 配置文件位置
| 配置 | 默认位置 | 作用 |
|---|---|---|
repository.xml | 从 jar 抽取,本文放 /opt/apache-jackrabbit/conf/ | 仓库全局配置:数据存储、安全、workspace、版本、搜索索引、集群 |
| workspace 模板 | 见 repository.xml 的 <Workspace name="${wsp.name}"> | 每个 workspace 的 file system / persistence / search index 模板 |
| 实例化 workspace 配置 | /opt/data/jackrabbit/workspaces/<ws>/ | 首次创建 workspace 时按模板生成 |
| 运行日志 | /opt/data/jackrabbit/log/jackrabbit.log、access.log.<日期> | 应用与访问日志 |
| 数据目录 | /opt/data/jackrabbit/ | repository / version / workspaces / tmp / log |
6.2 关键配置项(repository.xml)
<DataStore class="org.apache.jackrabbit.core.data.FileDataStore"/>:二进制数据存储,默认文件存储。<Security>/<LoginModule>:adminId默认admin,anonymousId默认anonymous。<Workspaces rootPath="${rep.home}/workspaces" defaultWorkspace="default"/>:workspace 根目录与默认 workspace 名。<Workspace>/<PersistenceManager>:workspace 持久化,本文改为BundleFsPersistenceManager(文件系统)。<Versioning>/<PersistenceManager>:版本存储持久化,同理改为BundleFsPersistenceManager。<SearchIndex class="...lucene.SearchIndex">:Lucene 全文索引,path 指向索引目录。<Cluster id="node1">/<Journal class="...MemoryJournal">:集群 journal(默认内存实现,单机可忽略)。
详见《Apache Jackrabbit 配置参数详解》。
6.3 JVM 堆内存限制
Jackrabbit 是 Java 进程,生产应按机器规格限制堆内存,避免沿用启动时未设限制导致的默认大堆。standalone 通过 java -jar 启动,-Xms/-Xmx 直接写在命令行:
nohup $JAVA_HOME/bin/java -Xms256m -Xmx512m -Xmn128m \
-jar jackrabbit-standalone-2.22.5.jar \
-c /opt/apache-jackrabbit/conf/repository-fs.xml \
-r /opt/data/jackrabbit > /tmp/jr.log 2>&1 &
其中 -Xms256m(初始堆 256MB)、-Xmx512m(最大堆 512MB)、-Xmn128m(新生代 128MB),符合 256–512MB 堆区间建议。
若用 systemd 托管,在 unit 里通过 Environment=JAVA_OPTS 注入(每行一个变量):
[Service]
Environment=JAVA_OPTS=-Xms256m -Xmx512m -Xmn128m
ExecStart=/usr/lib/jvm/java-17-openjdk-amd64/bin/java $JAVA_OPTS -jar /opt/apache-jackrabbit/jackrabbit-standalone-2.22.5.jar -c /opt/apache-jackrabbit/conf/repository-fs.xml -r /opt/data/jackrabbit
⚠️ 若用 Docker Compose 部署,通过
environment:注入JAVA_TOOL_OPTIONS(见《Apache Jackrabbit Docker Compose 部署指南》)。
验证窗口:确认实际生效的堆参数 用 jps -v 查看已运行 Java 进程的完整 JVM 参数(只能看到已生效的,即真实生效值):
$JAVA_HOME/bin/jps -v | grep jackrabbit
实测回显(明确可见 -Xms256m -Xmx512m -Xmn128m):
5134 jackrabbit-standalone-2.22.5.jar -Xms256m -Xmx512m -Xmn128m
七、注意事项
- Derby 驱动缺失:2.22.5 standalone 未内嵌 Derby 驱动,默认
repository.xml直接启动必失败,务必按「五、5.2」改为BundleFsPersistenceManager。 - 写内容节点用 WebDAV:
/repository/*走标准 WebDAV(MKCOL/PUT/PROPFIND),最稳;davE 读取走/server/*,创建复杂节点直接写 JCR 客户端代码。 - JVM 堆:始终显式设
-Xms/-Xmx,以jps -v确认生效。 - 密码与账号:本文演示账号
admin/q1w2e3r4为环境实测值;独立新装工厂默认密码为admin,见「八、常见问题」改密方式。 - 修改
repository.xml后需重启服务生效;仓库元数据(用户、密码、节点)持久化于/opt/data/jackrabbit,重启不丢(见 5.5 中重启后节点仍可读)。
八、常见问题
Q1:启动报 Could not load JDBC driver class org.apache.derby.jdbc.EmbeddedDriver?
原因:repository.xml 默认用 DerbyPersistenceManager,但 standalone jar 未打包 Derby 驱动。按「五、5.2」用 BundleFsPersistenceManager 替换两处即可。
Q2:/ 根路径访问返回 503?
正常。standalone 无根欢迎页,Jetty 默认 servlet 对 / 返回 503。管理入口是 /server/(workspace 概览)和 /repository/(WebDAV)。
Q3:davE 访问 /server/default/api 返回 500 Unexpected format of resource path?
该路径缺 jcr:root 前缀。应使用 /server/default/jcr:root/... 形态取节点,或直接用 WebDAV MKCOL/PUT 创建。
Q4:默认 admin 密码是什么?如何改成 q1w2e3r4?
工厂默认 admin/admin。可在服务停止后用 JCR UserManager.changePassword() 修改(参考 JcrOps 的登录写法取到 User 后调用 changePassword("q1w2e3r4") 并 save())。本指南环境已按此流程设为 admin/q1w2e3r4。
Q5:JVM 堆没生效?
用 jps -v 看真实进程参数;若通过 systemd/Compose 启动,检查注入变量是否真正传给 java(见三、六)。
九、卸载方式
- 停止服务(systemd 托管时):
systemctl stop jackrabbit
systemctl disable jackrabbit
- 删除安装目录、启动脚本与单元文件:
rm -rf /opt/apache-jackrabbit
rm -f /etc/systemd/system/jackrabbit.service
systemctl daemon-reload
- 如需连带清空数据(不可逆,谨慎):
rm -rf /opt/data/jackrabbit
若只卸 Java 进程 JDK:
apt-get purge -y openjdk-17-jdk-headless
rm -f /etc/profile.d/java.sh
十、参考链接
- Apache Jackrabbit 官网:https://jackrabbit.apache.org/
- Jackrabbit 下载目录(含版本列表):https://downloads.apache.org/jackrabbit/
- 本版本发行目录:https://downloads.apache.org/jackrabbit/2.22.5/
- Jackrabbit 2.x 配置文档(repository.xml):https://jackrabbit.apache.org/archive/jcr-2.0/jackrabbit-2.22/config.html
- JCR 2.0 规范(JSR 283):https://jcp.org/en/jsr/detail?id=283