jsr-283 - Java.net

martencrushInternet και Εφαρμογές Web

8 Δεκ 2013 (πριν από 3 χρόνια και 9 μήνες)

406 εμφανίσεις


1





Content Repository API
for Java™ Technology

Specification

Java Specification Request 283

version 2.0

Public Review

2 July

2007


2


1 PREFACE

13

1.1 Documents Included

13

1.2 Typographical Conventions

13

1.3 System Requirements

13

2 INTRODUCTION

14

2.1 Motivation

14

2.2 Goals

14

3 THE REPOSITORY MOD
EL

16

3.1 API Basics

17

3.1.1 Traversal Access

18

3.1.2 Direct Access

19

3.1.3 Writing to the Repository

20

3.1.4 Nodes, Properties and Items

22

3.2 Compliance Levels

22

3.3 Same

Name Siblings

23

3.3.1 Index Notatio
n

24

3.3.2 Support for Same Name Siblings is Optional

24

3.3.3 Properties Cannot Have Same Name Siblings

25

3.3.4 A Property and a Node Can Have the Same Name

25

3.4 Orderable Child Nodes

25

3
.4.1 Orderable Same Name Siblings

25

3.4.2 Non
-
orderable Child Nodes

26

3.4.3 Orderable Child Node Support is Optional

26

3.4.4 Properties are Never Orderable

26

3.5 Namespaces

26

3.6 Path Syn
tax

27

3.6.1 Names vs. Paths

28

3.6.2 Current Item and Parent Item

28

3.6.3 Exposing non
-
JCR Names

28

3.7 Properties

29

3.7.1 Multi
-
Value Properties

29

3.7.2 Property Types with Special Semantics

30

3.7.3 No Null Values

31

3.8 Node Types

31

3.9 Identifiers

32

3.9.1 Referenceable Identifiers

32

3.9.2 Referenceable Nodes

33

3.9.3 Reference Properties

34

3.9.4 Constructing Referenceable Identifiers

34

3.9.5 Hybrid and Other Non
-
referenceable Identifiers

34

3.9.6 Restricting Referenceable Nodes

35

3.9.7 When Id
entifiers are Assigned

35

3.10 Workspaces

35

3.10.1 Single Workspace Repositories

35

3.10.2 Multiple Workspaces and Corresponding Nodes

37

3.11 Versioning

39

3.12 Metadata

43

3.13 Hierarchical versus Direct Access

43

3.14 Use Cases

44

3.14.1 JCR in Source
Code Management

44

3.14.2 JCR and WebDAV/DeltaV

45

4 LEVEL 1 REPOSITORY

FEATURES

48

4.1 Accessing the Repository

49

4.1.1 Repository Construction

49

4.1.2 Repository Acquisition

50

4.1.3 Sample Code

50

4.1.4 Repository

52


3

4.1.5 Credentials

57

4.2 Reading Repository Content

59

4.2.1 Sessions and Workspaces

59

4.2.2 Type
s of Read Access

59

4.2.3 Effect of Access Denial on Read

60

4.2.4 Session Read Methods

61

4.2.5 Workspace Read Methods

64

4.2.6 Node Read Methods

65

4.2.7 Iterators

71

4.2.8 Property Read Methods

73

4.2.9 Property Types

78

4.2.10 Property Type Conversion

84

4.2.11 Value

89

4.2.12 Comparison of Values

94

4.2.13 Item Re
ad Methods

96

4.2.14 Example

99

4.3 Namespaces

102

4.3.1 Namespa
ce Registry

102

4.3.2 Prefix Syntax

104

4.3.3 Session Namespace Mappings

104

4.3.4 Transactions and Namespaces

106

4.4 XML Mappings

107

4.4.1 System View XML Mapping

107

4.4.2 Document View XML Mapping

110

4.4.3 Escaping of Names

113

4.4.4 Escaping of Valu
es

114

4.5 Exporting Repository Content

116


7.5.4.4

119

4.5.1 E
ncoding

119

4.6 Query

119

4.6.1 Introduction to the Abstract Query Model

120

4.6.2 Equality and Comparison

121

4.6.3 Query Validity

122

4.6.4 Search Scope

122

4.6.5 Notations

122

4.6.6 Abstract Query Model and Language Bindings

124

4.6.7 Query API

159

4.6.8 QueryManager

160

4.6.9 Query Object

161

4.6.10 PreparedQuery

165

4.6.11 Persistent vs. Transient Queries

165

4.6.12 QueryResult

166

4.6.13 Permissions

169

4.7 Node Types

170

4.7.1 What Constitutes a Node Type

170

4.7.2 Node Type Discovery in Level 1

171

4.7.3 Primary and Mixin Node Types

172

4.7.4 Special Properties
jcr:primaryType and jcr:mixinTypes

172

4.7.5 Property Definitions

173

4.7.6 Child Node Definitions

174

4.7.7 Inheritance Among Node Types

175

4.7.8 Discovering available Node Types

176

4.7.9 D
iscovering the Node Types of a Node

178

4.7.10 NodeTypeDefinition

179

4.7.11 NodeType

181

4.7.12 ItemDefinition

183

4.7.13 PropertyDefinition

185

4.7.14 NodeDefinition

186

4.7.15 Multiple Definitions with the Same Name

188

4.7.16 Residual Definitions

188

4
.7.17 Value Constraints

189

4.7.18 Automatic Item Creation

192


4

4.7.19 Discovery of Constraints on Existing Items

193

4.7.20 Root Node Type and Definition

194

4.7.21 Predefined Node Types

195

4
.7.22 Node Type Definitions in Content

197

4.7.23 Predefined Mixin Node Types

198

4.7.24 Predefined Primary Node Types

201

4.7.25 Custom Node Types

209

4.8 System Node

211

4.8.1 Non
-
hierarchic
al Content

211

4.9 Permission Checking

212

4.9.1 JAAS

212

4.9.2
Checking Permissions

212

4.10 JCR Address

214

5 LEVEL 2 REPOSITORY

FEATURES

215

5.1 Writing Repository Content

216

5.1.2 Saving by Identifier

221

5.1.3 Reflecting Item State

222

5.1.4 Adding Nodes

226

5.1.5 Adding and Writing Properties

228

5.1.6 Removing
Nodes and Properties

2
38

5.1.7 Moving and Copying

239

5.1.8 Updating and Cloning Nodes across Workspaces

246

5.1.9 Referenceable Nodes

248

5.1.10 Treatment of Identifiers

249

5.1.11 Ordering C
hild Nodes

250

5.2 Adding and Removing Workspaces

252

5.3 Adding and Deleting Namespaces

253

5.3.1 Visibility of Namespace Registry Changes

254

5.4 Importing Repository Content

255

5.4.1 Impor
t from System View

255

5.4.2 Importing Arbitrary XML

255

5.4.3 Respecting Property Semantics

257

5.4.4 Determining Node Types

258

5.4.5 Determining Property Types

258

5.4.6 Workspace Import Me
thods

259

5.4.7 Session Import Methods

263

5.4.8 Importing
jcr:root

267

5.5 Assigning Node Types

268

5.5.1 The Special Properties
jcr:primaryType and jcr:mixinTypes

268

5.5.2 Assigning a Prima
ry Node Type

268

5.5.3 Changing the Primary Type of a Node

268

5.5.4 Assigning Mixin Node Types

270

5.5.5 Automatic Addition and Removal of Mixins

272

5.6 Serialization and Node Types

272

5.7
Constraint Enforcement

273

5.8 Thread
-
Safety Requirements

273

6 OPTIONAL REPOSITOR
Y FEATURES

274

6.1 Transactions

275

6.1.1 Container Managed Transactions: Sample Request Flow

276

6.1.2 User M
anaged Transactions: Sample Code

276

6.1.3 Save vs. Commit

277

6.1.4 Single Session Across Multiple Transactions

277

6.1.5 Mention of Transactions within this Specification

278

6.2 Versioning

279

6.2.1 Versioning Concepts

279

6.3 Simple Versioning

281

6.3.1 Simple
-
Versionable

281

6.3.2 Initializing the Version History

281

6.3.3 Check In

282

6.3.4 Check Out

283


5

6.3.5 Checkpoint

284

6.3.6 Restoring a Version

284

6.3.7 Restoring a Group of Version
s

285

6.3.8 Update

285

6.3.9 Version Storage

285

6.4 Full Versio
ning

286

6.4.1 Versionable Nodes

287

6.4.2 Nested Versionable Nodes

288

6.4.3 Version Storage

289

6.4.4 The Base Version

296

6.4.5 Initializing the Version History

296

6.4.6 Check In

297

6.4.7 Check Out

299

6.4.8 Checkpoint

300

6.4.9 Restoring a Version

300

6.4.10 Restoring a Group of Versions

301

6.4.11 Update

301

6.4.12 Merge

302

6.4.13 Serialization of Version Storage

306

6.5 Ve
rsioning within a Transaction

306

6.6 Versioning API and On
-
Parent
-
Version

307

6.6.1 OnParentVersion Attribute

307

6.6.2 OnParentVersionAction Class

310

6.6.3 Versioning API

310

6.7 Activities
, Configurations and Baselines

325

6.7.1 Activities

325

6.7.2 Configurations and Baselines

329

6.8 Observation

332

6.8.1 Discovering Observation Support

332

6.8.2 Event Types

332

6.8.3 The Event Object

333

6.8.4 Asynchronous Observation

351

6.8.5 Journaled

Observation

355

6.8.6 Event Dispatch

357

6.8.7 Event Filtering

358

6.8.8 Example: Events for Common Operations

358

6.8.9 Deserializing Content

361

6.8.10 External Mechanisms

361

6.8.11 Location of Listeners

361

6.8.12 Persistence of Event Listeners

361

6.
8.13 Exceptions

361

6.9 Locking

362

6.9.1 Discovery of Lock Capabilities

362

6.9.2 Lockable

362

6.9.3 Shallow and Deep Locks

36
2

6.9.4 Lock Owner

363

6.9.5 Placing and Removing a Lock

363

6.9.6 Lock Token

364

6.9.7 Session
-
scoped and Open
-
scoped Locks

364

6.9.8 Effect of a Lock

365

6.9.9 Timing Out

365

6.9.10 Locks and

Transactions

366

6.9.11 Locking Methods

367

6.9.12 The Lock Object

369

6.9.13 Session Methods Related to the Lock Token

371

6.10 Node Type Registration

372

6.10.1 NodeTypeManager

372

6.10.2 NodeTypeTemplate

375

6.10.3 NodeDefinitionTemplate

376

6.10.4 Pro
pertyDefinitionTemplate

377

6.11 Access Control

379

6.11.1 Access Control Discovery

379


6

6.11.2 Access Control Management

384

6.11.3 Access Control Entries

387

6.12 Lifecycle Management

393

6.12.1 mix:lifecycle

394

6.12.2 Node Methods

394

6.13 Shareable Nod
es

395

6.13.1 Shared Sets

395

6.13.2 mix:shareable

395

6.13.3 Cr
eation of Shared Nodes

395

6.13.4 Removal of Shared Nodes

396

6.13.5 Child Nodes of Shared Nodes

397

6.13.6 Properties of Shared Nodes

398

6.13.7 Deemed Path

398

6.13.8 Diagram

399

6.13.9 Parents of Shared Nodes

399

6.13.10 Identifiers

400

6.13.11 Transien
t Layer

401

6.13.12 Copy

401

6.13.13 Share Cycles

401

6.13.14 Im
port and Export

401

6.13.15 Observation

402

6.13.16 Locking

402

6.13.17 Node Type Constraints

402

6.13.18 Versioning

402

6.13.19 Restore

402

6.13.20 Cloning

403

6.13.21 IsSame

403

6.13.22 RemoveMixin

403

6.13.23 Search

403

6.14 Retention and Hold Support

403

6.14.1 mix:managedRetention

404

6.14.2 Retention and Hold API

404

7 APPENDICES

407

7.1 Appendix A: Naming Conventions

407

7.2 Appendix B: Compact Node Type Definition

408

7.2.1 Grammar

408

7.2.2 Structure of a CND

409

7.3 Appendix C: XML Node Type Definition

415

7.4 Appendix D: JCR 1.0 XPath (Deprecated)

416

7.4.1 XPath over Document View

416

7.4.2 XPath and SQL

417

7.4.3 Struct
ure of a Query

417

7.4.4 Adapting XPath to the Content Repository

424

7.4.5 XPath Extensions

429

7.4.6 XPath Grammar

433

7.5 Appendix E: JCR 1.0 SQL Search (Deprecated)

438

7.5.1 The SQL Langu
age

438

7.5.2 Database View

438

7.5.3 SQL EBNF

443

7.5.4 SQL Syn
tax in Detail

444

7.5.5 Query Results

447



7

Acknowledgements

This specification is the collaborative product of

David Nuescheler

(specification lead, Day Softwa
re),

Peeter Piegaze

(author, Day Software),


and other members of the JSR 170 and JSR 283 expert groups,
including

Razmik Abnous

(EMC

Documentum
),

Tim Anderson

(Intalio),

Gordon Bell

(Hummingbird),

Tobias Bocanegra
(Day Software),

Al Brown
(FileNet),

Dave
Caruana
(Alfresco),

Geoffr
e
y Clemm

(IBM),

David Choy

(IBM),

Jeff Collins

(Vignette),

Cornelia Davis
(EMC

Documentum
),

Chenggang Duan
(Oracle),

Roy Fielding
(Day Software),

Xaver Fischer
(Opentext),

Gary Gershon
(Imerge),

Stefan Guggisberg

(Day Software),

F
lorent Guillaume

(
Nuxeo
),

Rich Howarth

(
IBM
),

Alison Macmillan

(
Oracle
),

Ryan McVeigh

(
BEA
),

Stefano Mazzocchi

(Apache Software Foundation),

James Myers

(Pacific Northwest National Laboratories),

John Newton
(Alfresco),

James Owen

(BEA),

Franz Pfeifroth

(F
ujitsu),


8

David Pitfield

(Oracle),

Corprew Reed

(FileNet),

Julian Reschke
(greenbytes),

Marcel Reutegger
(Day Software),

Celso Rodriguez
(Mobius),

Steve Roth
(BEA Systems),

Angela Schreiber

(Day Software),

Victor Spivak

(
EMC
Documentum),

Paul Taylor

(IBM)

D
avid B. Victor

(IBM),

Dan Whelan
(FileNet),

Kevin Wiggen
(Xythos),

Jukka Zitting
(Yukatan
, Apache Software Foundation
)

as well as many others who contributed with corrections and
suggestions.


9

License

DAY MANAGEMENT AG IS WILLING TO LICENSE THIS
SPECIFICAT
ION TO YOU ONLY UPON THE CONDITION THAT YOU
ACCEPT ALL OF THE TERMS CONTAINED IN THIS LICENSE
AGREEMENT ("AGREEMENT"). PLEASE READ THE TERMS AND
CONDITIONS OF THIS AGREEMENT CAREFULLY. BY DOWNLOADING
THIS SPECIFICATION, YOU ACCEPT THE TERMS AND CONDITIONS
OF THIS AGREEMENT. IF YOU ARE NOT WILLING TO BE BOUND BY
THEM, SELECT THE "DECLINE" BUTTON AT THE BOTTOM OF THIS
PAGE AND THE DOWNLOADING PROCESS WILL NOT CONTINUE.

Specification: JSR 283 Content Repository for Java
TM

Technology API Version 2.0 ("Specifica
tion")

Version: 2.0 (
Public Review
)

Status:
Pre
-
FCS Public R
elease

Release:
2 July

2007

Copyright 200
7

Day Management AG
,
Barfuesserplatz 6, 4001
Basel, Switzerland
.
All rights reserved.

NOTICE

The Specification is protected by copyright and the informat
ion
described therein may be protected by one or more U.S. patents,
foreign patents, or pending applications. Except as provided under
the following license, no part of the Specification may be
reproduced in any form by any means without the prior written
authorization of Day Management AG and its licensors, if any. Any
use of the Specification and the information described therein will
be governed by the terms and conditions of this Agreement.

Subject to the terms and conditions of this license, including
your
compliance with Paragraphs 1, 2 and 3 below, Day Management AG
hereby grants you a fully
-
paid, non
-
exclusive, non
-
transferable,
limited license (without the right to sublicense) under Day
Management AG's intellectual property rights to:

1. Review the
Specification for the purposes of evaluation. This
includes: (i) developing implementations of the Specification for
your internal, non
-
commercial use; (ii) discussing the Specification
with any third party; and (iii) excerpting brief portions of the
Speci
fication in oral or written communications which discuss the
Specification provided that such excerpts do not in the aggregate
constitute a significant portion of the Specification.

2. Distribute implementations of the Specification to third parties
for th
eir testing and evaluation use, provided that any such
implementation:

(i) does not modify, subset, superset or otherwise extend the
Licensor Name Space, or include any public or protected packages,
classes, Java interfaces, fields or methods within the Li
censor Name

10

Space other than those required/authorized by the Specification or
Specifications being implemented;

(ii) is clearly and prominently marked with the word "UNTESTED? or
"EARLY ACCESS" or "INCOMPATIBLE" or "UNSTABLE" or "BETA" in
any list of avai
lable builds and in proximity to every link initiating
its download, where the list or link is under
Licensee's

control; and

(iii) includes the following notice:

"This is an implementation of an early
-
draft specification developed
under the Java Community
Process (JCP) and is made available for
testing and evaluation purposes only. The code is not compatible
with any specification of the JCP."

3. Distribute applications written to the Specification to third parties
for their testing and evaluation use, prov
ided that any such
application includes the following notice:

"This is an application written to interoperate with an early
-
draft
specification developed under the Java Community Process (JCP)
and is made available for testing and evaluation purposes only.

The
code is not compatible with any specification of the JCP."

The grant set forth above concerning your distribution of
implementations of the Specification is contingent upon your
agreement to terminate development and distribution of your
implementatio
n of early draft upon final completion of the
Specification
.
If you fail to do so, the foregoing grant shall be
considered null and void.

Other than this limited license, you acquire no right, title or interest
in or to the Specification or any other Day M
anagement AG
intellectual property, and the Specification may only be used in
accordance with the license terms set forth herein. This license will
expire on the earlier of: (a) two (2) years from the date of Release
listed above; (b) the date on which th
e final version of the
Specification is publicly released; or (c) the date on which the Java
Specification Request (JSR) to which the Specification corresponds
is withdrawn. In addition, this license will terminate immediately
without notice from Day Manag
ement AG if you fail to comply with
any provision of this license. Upon termination, you must cease use
of or destroy the Specification.

"Licensor Name Space" means the public class or interface
declarations whose names begin with "java", "javax", "com.day
" or
their equivalents in any subsequent naming convention adopted
through the Java Community Process, or any recognized successors
or replacements thereof

TRADEMARKS


11

No right, title, or interest in or to any trademarks, service marks, or
trade names of Da
y Management AG or Day Management AG's
licensors is granted hereunder. Java and Java
-
related logos, marks
and names are trademarks or registered trademarks of Sun
Microsystems, Inc. in the U.S. and other countries.

DISCLAIMER OF WARRANTIES

THE SPECIFICATIO
N IS PROVIDED "AS IS" AND IS EXPERIMENTAL
AND MAY CONTAIN DEFECTS OR DEFICIENCIES WHICH CANNOT
OR WILL NOT BE CORRECTED BY DAY MANAGEMENT AG. DAY
MANAGEMENT AG MAKES NO REPRESENTATIONS OR WARRANTIES,
EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO,

WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
PURPOSE, OR NON
-
INFRINGEMENT THAT THE CONTENTS OF THE
SPECIFICATION ARE SUITABLE FOR ANY PURPOSE OR THAT ANY
PRACTICE OR IMPLEMENTATION OF SUCH CONTENTS WILL NOT
INFRINGE ANY THIRD PARTY PATENTS, COP
YRIGHTS, TRADE
SECRETS OR OTHER RIGHTS. This document does not represent
any commitment to release or implement any portion of the
Specification in any product.

THE SPECIFICATION COULD INCLUDE TECHNICAL INACCURACIES
OR TYPOGRAPHICAL ERRORS. CHANGES ARE PER
IODICALLY
ADDED TO THE INFORMATION THEREIN; THESE CHANGES WILL BE
INCORPORATED INTO NEW VERSIONS OF THE SPECIFICATION, IF
ANY. DAY MANAGEMENT AG MAY MAKE IMPROVEMENTS AND/OR
CHANGES TO THE PRODUCT(S) AND/OR THE PROGRAM(S)
DESCRIBED IN THE SPECIFICATION AT
ANY TIME. Any use of such
changes in the Specification will be governed by the then
-
current
license for the applicable version of the Specification.

LIMITATION OF LIABILITY

TO THE EXTENT NOT PROHIBITED BY LAW, IN NO EVENT WILL DAY
MANAGEMENT AG OR ITS LICE
NSORS BE LIABLE FOR ANY
DAMAGES, INCLUDING WITHOUT LIMITATION, LOST REVENUE,
PROFITS OR DATA, OR FOR SPECIAL, INDIRECT, CONSEQUENTIAL,
INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND
REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF OR
RELATED TO AN
Y FURNISHING, PRACTICING, MODIFYING OR ANY
USE OF THE SPECIFICATION, EVEN IF DAY MANAGEMENT AG
AND/OR ITS LICENSORS HAVE BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.

You will hold Day Management AG (and its licensors) harmless from
any claims based on
your use of the Specification for any purposes
other than the limited right of evaluation as described above, and
from any claims that later versions or releases of any Specification
furnished to you are incompatible with the Specification provided to
you
under this license.


12

RESTRICTED RIGHTS LEGEND

If this Software is being acquired by or on behalf of the U.S.
Government or by a U.S. Government prime contractor or
subcontractor (at any tier), then the Government's rights in the
Software and accompanying do
cumentation shall be only as set
forth in this license; this is in accordance with 48 C.F.R. 227.7201
through 227.7202
-
4 (for Department of Defense (DoD)
acquisitions) and with 48 C.F.R. 2.101 and 12.212 (for non
-
DoD
acquisitions).

REPORT

You may wish to r
eport any ambiguities, inconsistencies or
inaccuracies you may find in connection with your evaluation of the
Specification ("Feedback"). To the extent that you provide Day
Management AG with any Feedback, you hereby: (i) agree that
such Feedback is provid
ed on a non
-
proprietary and non
-
confidential basis, and (ii) grant Day Management AG a perpetual,
non
-
exclusive, worldwide, fully paid
-
up, irrevocable license, with
the right to sublicense through multiple levels of sublicensees, to
incorporate, disclose,
and use without limitation the Feedback for
any purpose related to the Specification and future versions,
implementations, and test suites thereof.

GENERAL TERMS

Any action related to this Agreement will be governed by California
law and controlling U.S. f
ederal law. The U.N. Convention for the
International Sale of Goods and the choice of law rules of any
jurisdiction will not apply.

The Specification is subject to U.S. export control laws and may be
subject to export or import regulations in other countri
es. Licensee
agrees to comply strictly with all such laws and regulations and
acknowledges that it has the responsibility to obtain such licenses
to export, re
-
export or import as may be required after delivery to
Licensee.

This Agreement is the parties' e
ntire agreement relating to its
subject matter. It supersedes all prior or contemporaneous oral or
written communications, proposals, conditions, representations and
warranties and prevails over any conflicting or additional terms of
any quote, order, ackn
owledgment, or other communication
between the parties relating to its subject matter during the term of
this Agreement. No modification to this Agreement will be binding,
unless in writing and signed by an authorized representative of
each party.


13

1

Preface

This is version 2.0 of the Content Repository API for Java
Technology specification (Java Specification Request 283). Versions
1.0 and 1.0.1 of this specification were released under Java
Specification Request 170.

1.1

Documents Included

The specification inc
ludes:



This document.



The Java source code for the API package
javax.jcr
and
subpackages.



A jar file of the API package
javax.jcr

and subpackages.



The Javadoc produced from the
javax.jcr

and subpackages.

In case of a di
screpancy between this document and the Javadoc
produced from the
javax.jcr

package, this document should be
considered normative.

1.2

Typographical
Conventions

A monospaced font is used for the following:



JCR names (the names of JCR nodes, properties,
node
ty
pes

and property types
). For example,
nt:base
,
jcr:created

and
REFERENCE.



Java
variables,
classes, interfaces and primitive types
. For
example,
Session
,
Node

and
boolean
.



URIs
. For example,
http://www.jcp.org.

Unless otherwise indicated all Java classes an
d interfaces
mentioned are in the package
javax.jcr

and its subpackages.
N
on
-
JCR classes mentioned are
always
fully qualified,
for example,

java.security.Principal
. The only exception is
java.lang.String
, which is used throughout and written simply as
Stri
ng
.

Code examples are written in
monospaced font
with a gray
background
, for example
:

/*


* This is an example of a code block.


*


*/

1.3

System Requirements

The JCR 2.0 API requires Java Runtime Environment (JRE) 1.4 or
greater.

14

2

Introduction

2.1

Motivation

As th
e number of vendors offering proprietary content repositories
has increased, the need for a common programmatic interface to
these repositories has become apparent. The aim of the Content
Repository for Java Technology API specification is to provide such
an interface and, in doing so, lay the foundations for a true
industry
-
wide content infrastructure.

Application developers and custom solution integrators will be able
to avoid the costs associated with learning the particular API of
each repository vendor
. Instead,

programmers will be able to
develop content
-
based application logic independently of the
underlying repository architecture or physical storage.

Customers will also benefit by being able to exchange their
underlying repositories without touching

any of the applications
built on top of them.

2.2

Goals

The guiding principles governing the design of the API are:

It should not be tied to any particular underlying
architecture, data source or protocol.

The API is, of course, essentially a set of Java inte
rfaces, which can
be implemented in a wide variety of ways. Hence, achieving this
goal is not difficult in itself. The main challenge here is to allow
enough flexibility in the API so that it can be used for both
hierarchical and non
-
hierarchical repositor
y models. This is done by
providing for both
hierarchical, path
-
based addressing

of content
items and
direct,
identifier
-
based addressing
.

It should be easy to use from the programmer’s point of
view.

To this end, the API is designed to be as simple and st
raightforward
as possible. In particular, it has a simple object model and
concentrates on representing the core functionality of a content
repository without venturing into areas that might be regarded as
“content applications”.

It should allow for relati
vely easy implementation on top of
as wide a variety of existing content repositories as possible.

A concerted effort was made to ensure that it would be relatively
easy to implement the API (especially at level 1, see below) on top
of the repositories of
most major vendors.


15

However, it should also standardize some more complex
functionality needed by advanced content
-
related
applications.

Recognizing that a tension exists between this aim and the previous
one, this specification has been split into two com
pliance levels as
well as a set of optional features.

Level 1 defines a read
-
only repository. This includes functionality
for the reading of repository content, introspection of content
-
type
definitions, basic support for namespaces, export of content to X
ML
and searching. This functionality should meet the needs of
presentation templates and basic portal applications comprising a
large portion of the existing code
-
base of content
-
related
applications. Level 1 is also designed to be easy to implement on
top

of any existing content repository.

Level 2 additionally defines methods for writing content,
assignment of types to content, further support for namespaces,
and importing content from XML.

Finally, a number of independently optional features are defined
that a compliant repository may support. These are transactions,
versioning, observation, access control, locking and additional
support for searching.


16

3

The Repository Model

A content repository consists of one or more
workspaces
, each of
which contains a
tree of
items
. An item is either a
node

or a
property
.
Each node may have zero or more child nodes and zero
or more child properties. There is a single root node per workspace,
which has no parent. All other nodes have one parent. Properties
have one paren
t (a node) and cannot have children; they are the
leaves of the tree. All of the actual content in the repository is
stored within the values of the properties.


In the diagram above, we see the single root node of some
workspace with child nodes
a
,
b

and

c
, each of which have further
child nodes or properties. For example, the node
a

has two child
nodes,
d

and
e
. Node
e
, in turn, has two properties,
j

and
k
. The
property
j

contains an image (a picture of a rabbit) and
k

contains
a floating
-
point number (
6
.022 × 10
23
). Similarly, the property
i

contains a boolean value (
true
), the property
g

contains a string
(

Once upon a time...

) and the property
h

contains an integer (
-
25
).

true

[root]


a


b


c


e

g

h


i


j

6.022

×

10
23

"Once upon
a time..."

-
25


k


d


node

property



17

Every item in a workspace apart from the root node has a non
-
empty
name
. The roo
t node always has the empty string as its
name.

Two properties with the same parent cannot have the same name.

A property and a node with the same parent may have the same
name.

Two or more nodes with the same parent
may

in some
circumstances have the same

name, in which case they are
distinguished by
index

(see
3.3

Same
-
Name Siblings

for more
details).

The chain of names from the root to any item defines the
absolute
path

of that item. For example, the path
/

refers to the root

node
and the path
/a/d/i

refers to the property with value
true
.
Absolute paths always begin with a
/

character.

A
relative path

specifies a node or property relative to another
location within the hierarchy. For example, relative to node
/a

in
the above
diagram, the path to the property with value
true

is
d/i
.
The Unix
-
style path segments “
.
” and “
..


(meaning respectively,
“this” and “parent”) are also supported so that, relative to
/a
, the
property containing the value

25

would be
../c/h
.
Relative path
s
are distinguished from absolute paths by having
no

leading
/

character.

3.1

API Basics

The repository as a whole is represented by a
Repository

object
1
.
A client connects to the repository by calling
Repository.login

optionally specifying a workspace name an
d a
Credentials

object
2
.
The client then receives a
Session

object tied to the specified
workspace.

The
Repository

object is acquired through the Java Naming and
Directory (JNDI) API (see
4.1

Accessing the Repository
).

// Get t
he Repository object

InitialContext ctx = ...

Repository repository = (Repository)ctx.lookup("myrepo");





1

Unless otherwise noted, all references to “objects” refer to
instances of Java classes implementing the indicated Java interf
ace
from the
javax.jcr

package and subpackages. For example, the
term “
Repository

object” means an instance of a class
implementing the interface
javax.jcr.Repository
.

2

There are other signatures of
login

as well. See
4.1.4

Repository

for details.


18


The specifics of acquiring the
Credentials

object are not specified.
Below we show one possibility: using the class
SimpleCredentials

included in the
specification. Implementations may provide their
own
Credentials

classes as well.

// Get a Credentials object

Credentials credentials =


new SimpleCredentials("MyName",


"MyPassword".toCharArray());



The
Repository.login

method r
eturns a Session object.

// Get a Session

Session mySession =


repository.login(credentials, "MyWorkspace");



Through the
Session

object the client can access any node or
property in that tree of the workspace to which the
Session

is tied.
The API provid
es methods for both traversing the tree step by step
and for directly accessing a particular item.

3.1.1

Traversal Access

Traversal access typically begins with

Node Session.getRootNode()
.

From the returned root node, successive levels of child nodes can
be acce
ssed with

Node Node.getNode(String relPath)
,

which takes a relative path (so it can skip down or up multiple
levels as well). There is also a similar method for accessing
properties,

Property Node.getProperty(String relPath)
.

The data stored in the propert
y can be accessed either directly with
methods like

String Property.getString()
,

or in the form of a type
-
neutral wrapper, the
Value

object, using

Value Property.getValue()
.

The actual data can then be retrieved with, for example,

String Value.getString()
.

Here is an example code snippet:

// Get the root node


19

Node root = mySession.getRootNode();


// Traverse to the node you want

Node myNode = root.getNode("a/e");


// Retrieve a property of myNode

Property myProperty = myNode.getProperty("k");


// Get the va
lue of the property

Value myValue = myProperty.getValue();


// Convert the value to the desired type

double myDouble = myValue.getDouble();


// The variable myDouble will contain the

// value 6.022 x 10^23


3.1.2

Direct Access

The most important direct access me
thod
s

are

Node

Session.get
Node
(String abspath)
.

and

Property Session.getProperty(String absPath)

Th
ese

method
s

take an absolute path and
return

the indicated node
or property:

// Directly get the property with

// the value of Avogadro's Number

// (i.e., 6.
022 x 10^23)

Property myProperty =

mySession.get
Property
("/a/e/k");


// Directly convert to a double

double myDouble = myProperty.getDouble();


// The variable myDouble will contain the

// value 6.022 x 10^23



Another direct access method (though for node
s only, not
properties) is,

Node Session.getNodeByI
dentifier
(String id
entifier
)
.

This method can be used to access
a
node
by
its
identifier

(see
3.9

Identifiers
)
:

// Assuming that the node /a/e is referenceable

// and has ID 1
2
34567890
, we get it

Node myNode =


mySession.getNodeByI
dentifier
("
1234567890
");


// and then get the property and convert it to a double

double myDouble = myNode.getProperty("k").getDouble();


// The variable myDouble will contain the


20

// value 6.022 x
10^23



3.1.3

Writing to the Repository

If the repository is level 2 compliant (see
3.2

Compliance Levels
)
then, having acquired a session, the client can write to the
repository by adding or removing nodes and properties or changing

the values of properties.

For example, the client can retrieve a node, add a child node to it
and add a property to that child node:

// Retrieve a node

Node myNode = mySession.
get
Node
("/a/e");


// Add a child node

Node newNode = myNode.addNode("n");


// A
dd a property

newNode.setProperty("x", "Hello");


// Persist the changes

mySession.save();



The node
myNode

has the path
/a/e
, so the new node will have path
/a/e/n
and the new property will have the path
/a/e/n/x
and the
string value “
Hello
”.

3.1.3.1

Removing It
ems

To erase an item, the method
Item.remove()

is used. For example,
continuing from the above code segment, the following code,

// Remove the node /a/e (and its subtree)

myNode.remove();


// Persist the changes

mySession.save();


would result in the node
at
/a/e

(and its child node
/a/e/n
) being
deleted.

In the case of
Properties
, an alternative to
remove

is to set the
property to
null
. This can be done in two ways, by calling
setValue

with
null

on the property itself, or by calling
setProperty

with the pr
operty name and a
null

value on the
property's parent node:

// Assume we have node /m and two

// properties /m/p and /m/q

Node m = mySession.get
Node
("/m");

Property p = m.getProperty("p");


//Remove p by calling setValue on p itself


21

p.setValue((Value)null)
;


//Remove q by calling setProperty on q's parent node

m.setProperty("q", (Value)null);


// Persist the changes

mySession.save();



See
3.7.3

No Null Values.

3.1.3.2

Transient Storage in the Session

Notice the use of the method
Sessio
n.save

in the above examples.
This method is needed because changes made through most
methods of
Session
,
Node
3

or
Property

are not immediately
reflected in the persistent workspace. The changes are held in
transient storage associated with the
Session

obj
ect until they are
either persisted (using
Session.save

or
Item.save
) or discarded
(using
Session.refresh(false)

or
Item.refresh(false)
).

Changes not yet saved or discarded are called
pending changes
.
Pending changes are immediately visible through the ses
sion that
made them but are not visible through other sessions accessing the
same workspace.

Session.save

validates and, if validation succeeds, persists all
pending changes currently stored in the
Session

object, making
them visible to other sessions (tho
ugh this only applies if the
save

is not within the scope of a transaction, see
3.1.3.3

Transactions
,
below). Conversely,
Session.refresh(false)

discards all pending
changes currently stored in the
Session
.

For more fine
-
graine
d control over which changes are persisted or
discarded, the methods
Item.save

and
Item.refresh

are also
provided.
Item.save
saves all pending changes in the
Session

that
apply to that particular item or its subtree. Analogously,
Item.refresh(false)

discar
ds all pending changes that apply to
that item or its subtree. See
5.1

Writing Repository Content
.

3.1.3.3

Transactions

Throughout this document, any discussion of “persistence of
changes upon
save
” or “immediate persistence of changes

through
methods that do not require
save
” refers to cases in which the
save

is performed
outside the scope of a transaction
.




3

Some

Node

methods act immediately on the persistent workspace
and do not require
save
. See
5.1.1.2

Writing Directly to the
Workspace
.


22

Within the scope of a transaction,
save

and other methods that act
directly on the persistent workspace will
not

make changes visi
ble
to other sessions; this will only occur when the transaction is
committed.

However, even within the scope of a transaction,
save

still performs
validation and, if successful, clears pending changes from the
Session
. As well,
refresh(false)

still clears

pending changes
from the
Session
.

When a transaction commits, it persists only those changes that
have been saved; it does
not

automatically
save

pending changes
and then

commit them as well. After a commit, pending changes
remain in the
Session

and may b
e saved and committed later.
Note that support for transactions is optional. See
6.1

Transactions
.

3.1.4

Nodes, Properties and Items

Because nodes and properties have some common functionality,
common methods are defined in the inter
face
Item
, to which the
subclasses
Node

and
Property

add further methods. The following
diagram summarizes the basic relationships between the interfaces.

This UML diagram indicates that
Property

and
Node

are subclasses
of
Item
. A single
Property

has one
and only one parent
Node
. A
Node

can have either zero parents (only if it is the root node) or
one parent. A
Node

can have any number of child
Item

objects (i.e.,
either
Property

or
Node

objects).

3.2

Compliance Levels

This specification is divided into two co
mpliance levels and a set of
additional optional features which repositories of either level may
support. Level 1 provides for read functions and level 2 adds
additional write functions. The functional division is as follows:

Level 1 includes:



Retrieval an
d traversal of nodes and properties

Item

Node

Property

1

*

*

1

0..1

*

child

parent

parent


23



Reading the values of properties



Transient namespace remapping



Export to XML/SAX



Search using both a SQL
-
like syntax and a query
-
tree Java
API



Discovery of available node types



Discovery of access control permissions

Lev
el 2 adds
:



Adding and removing nodes and properties



Writing the values of properties



Persistent namespace changes



Import from XML/SAX



Assigning node types to nodes



Creating and Deleting Workspaces

Optional:

Any combination of the following features may be
added to an
implementation of either level.



Transactions



Versioning



Observation (Events)



Locking



Node Type Registration



Access Control



Lifecycle management



Multiple Hierarchies

3.3

Same

Name Siblings

A particular node
may
, in some cases, have
same
-
name sibling
s
,
that is, other nodes that share its parent and have the same name.
Whether a particular node allows this depends on the
child
-
node
definition

that applies to it (this definition is part of the node type of
that node’s parent, see section
4.7

Node Types
).

The standard method for retrieving a set of such nodes is
Node.getNodes(String namePattern)

which returns an iterator

24

over all the child nodes of the calling node that have the specified
pattern (by making
namePattern

just a
name, without wildcards,
we can get all the nodes with that exact name, see section
4.2.6

Node Read Methods
).

3.3.1

Index Notation

A particular node within a same
-
name sibling group can be
addressed by embedding an array
-
like no
tation within the path. For
example the path
/a/b[2]/c[3]

specifies the third child node called
c

of the second child node called
b

of the node
a

below the root.

The indexing of same
-
name siblings begins at
1
, not
0
. T
his practice
stems from
JCR 1.0 where
compatibility with
XPath

was required.

A

name in a content repository path that does not explicitly specify
an index implies an index of
1
. For example,
/a/b/c

is equivalent to
/a[1]/b[1]/c[1]
.

The indexing is based on the order in which child nodes are
r
eturned in the iterator acquired through
Node.getNodes()
.

Same
-
name siblings are indexed by their position relative to each
other in this larger ordered set
.
For example, the order of child
nodes returned by a
getNodes

on some parent might be:

[A, B, C, A,

D]

In this case,
A[1]

refers the first node in the list and
A[2]

refers to
the fourth node in the list.

If a node with same
-
name siblings is removed, this decrements by
one the indices of all the siblings with indices greater than that of
the removed node
. In other words, a removal compacts the array
of same
-
name siblings and causes the minimal re
-
numbering
required to maintain the original order but leave no gaps in the
numbering.

Note that regardless of whether orderable child nodes are
supported in gene
ral (see
3.4

Orderable Child Nodes
), the relative
ordering of a set of same name sibling nodes must be persistent; it
cannot change arbitrarily between read method calls or between
sessions. This requirement stems from the fact

that the path of a
node must not change arbitrarily, and in the case of a same
-
name
sibling, its position relative to its co
-
named siblings defines part of
its path.

3.3.2

Support for Same Name Siblings is Optional

As mentioned, whether or not a particular node

allows multiple
child items with the same name is governed by the
node type

of
that particular node. See
4.7

Node Types
.


25

Though there is a required set of node types that every compliant
repository must support, none of these
required node types allow
same
-
name siblings and any further node types available in a
particular repository are implementation
-
specific. Therefore, it is
possible for a repository to disallow same
-
name siblings altogether
by restricting the set of availab
le node types.

3.3.3

Properties Cannot Have Same Name Siblings

Properties cannot have sibling properties of the same name.
However, they may have multiple values. See
3.7.1

Multi
-
Value
Properties
, below.

3.3.4

A Property and a Node
Can H
av
e the Same Name

A property and a node which have the same parent may have the
same name.
T
he methods

Node.getNode, Session.getNode,

Node.getProperty

and

Session.getProperty

obviously specify
whether the desired item is a node or a property. The method
Sess
ion.getItem

will return the item at the specified path if there
is only one such item, if there is both a node and a property at the
specified path,
getItem

will return the node.

3.4

Orderable Child Nodes

Some nodes may support client
-
controlled ordering of th
eir child
nodes. Whether a particular node preserves the order of its child
nodes is governed by its node type. See
4.
7

Node Types
.

If a node supports orderable child nodes, the order of its child
nodes, as reflected in the ite
rator acquired through
Node.getNodes()

can be controlled by the client using the method
Node.orderBefore
. The order of child nodes is persisted upon
save

of the parent node.

When a child node is added to a node that supports orderable child
nodes it is add
ed to the end of the list. It can then be re
-
ordered
using the above method.

3.4.1

Orderable Same Name Siblings

If the parent node supports orderable child nodes
and

same
-
name
siblings then the same
-
name sibling child nodes will be orderable
by the application j
ust like an
y

other child nodes. For example,
given the following initial ordering of child nodes,

[A, B, C, A, D]

a call to

orderBefore("A[2]","A[1]")


26

will cause the child node currently called
A[2]

to be moved to the
position before the child node current
ly called
A[1]
, the resulting
order will be:

[A, A, B, C, D]

where the first
A

is the one that was formerly after
C

and the
second
A

is the one that was formerly at the head of the list.

Note, however, that after the completion of this operation
the
indice
s of the two nodes have now switched
, due to their new
positions relative to each other. What was formerly
A[2]

is now
A[1]

and what was formerly
A[1]

is now
A[2]
.

3.4.2

Non
-
orderable Child Nodes

When a node does not support orderable child nodes this means
that

it is left up to the implementation to maintain the order of child
nodes. Applications should not, in this case, depend on the order of
child nodes returned by
Node.getNodes
, as it may change at any
time. The only exception to this rule is that same
-
name
siblings
must maintain their relative order across read method invocations
and across sessions.

3.4.3

Orderable Child Node Support is Optional

Like same name siblings, support for orderable child nodes depends
on the range of node types available in a particular

repository.
Orderable child nodes are not mandated by any required node
types, and any additional node types are implementation
-
specific.
Therefore, orderable child node support is, in effect, optional.

3.4.4

Properties are Never Orderable

Properties are never
client orderable, the order in which properties
are returned by
Node.getProperties

is always maintained by the
implementation and can change at any time.

3.5

Namespaces

The name of a node or property may have a
prefix
, delimited by a
single '
:
' (colon) charact
er that indicates the
namespace

of the
item.

Namespacing in a content repository is patterned after
namespacing in XML. As in XML, the prefix is actually shorthand for
the full namespace, which is a URI
.
URIs are used as namespaces
in order to minimize nam
ing collisions. Every compliant (level 1 or
2) repository has a namespace registry. The namespace registry
always contains at least the following built
-
in namespace prefixes:



jcr
Reserved for items defined within built
-
in node types.



nt
Reserved for the na
mes of built
-
in primary node types.


27



mix

Reserved for the names of built
-
in mixin node types.



xml

Reserved for reasons of compatibility with XML.



“” (the empty prefix) This indicates the default namespace.

In level 1 repositories the prefix assigned to an e
xisting registered
namespace (a URI) may be temporarily over
-
ridden by another
prefix within the scope of a particular
Session
. Level 2 repositories
have, additionally, the capability to add, remove and change the set
of namespaces (URIs) stored in the nam
espace registry (excluding
the built
-
in namespaces). See section
4.3

Namespaces
, for more
details.

3.6

Path Syntax

A syntactically valid path is:

path ::= abspath | relpath


abspath ::= '/' relpath | '/'


relpath ::= pathelement |
relpath '/' pathelement


pathelement ::= name | name '[' number ']' | '..' | '.'


number ::= /* An integer > 0 */


name ::= [prefix ':'] simplename


simplename ::= onecharsimplename |


twocharsimplename |


threeormorecharname


o
necharsimplename
::= /* Any
XML Char
4

except:


'.', '/', ':', '[', ']', '*'
,




'|' or any whitespace


character */


twocharsimplename ::= '.' onecharsimplename |


on
echarsimplename '.' |


onecharsimplename onecharsimplename


threeormorecharname ::= nonspace string nonspace


prefix ::= /* Any valid non
-
empty XML NCName */


string ::= char | string char


char ::= nonspace | ' '


nonspace ::= /* Any
XML Char

except:


'/', ':', '[', ']', '*', '|'


or any whitespace




4

See
http://www.w3.org/TR/REC
-
xml/

for

the definition of XML
Char.


28


character */

3.6.1

Names vs. Paths

A “name” is valid if satisfies the above
name

production. It can be
thought of, informally, as a single path elemen
t
without any
square
-
bracket index
(and not including the '.' and '..'). For
example,
myapp:paragraph

is a
name

and a valid
relative path

(of
depth 1) whereas,
myapp:paragraph[3]

is not a name, it is only a
relative path.

Names and paths are not simply str
ings with certain syntax. They
have special semantics in that they respect the namespace
mappings of the current
Session

(see
4.3

Namespaces
). The
special property types
NAME

and
PATH

are provided to enable the
storage of these

values in the repository in a namespace
-
sensitive
way (see
4.2.9

Property Types

a
nd

3.7

Properties
).

3.6.2

Current Item and Parent Item

The
syntax of paths includes the segments “
.
” and “
..
” indicating
current item and parent item, respectively. These can be used
within JCR paths just as they can in Unix
-
like file system paths. For
example,
/a/b/../c

is equivalent to
/a/c

while
/a/b/./c

is
equ
ivalent to
/a/b/c
, assuming that that the items
a
,
b

and
c

exist,
and the session using these paths has access to these items
.

Paths
are resolved
as though

each segment were processed in turn.
Implementations, of course, are free to optimize how they resol
ve
paths provided that this semantic is preserved
.
This means for the
example above, if
b

does not exist, or the session using the path
does not have access to
b
, the path resolution would fail.

3.6.3

Exposing
non
-
JCR

Names

A
n

implementation
that
expose
s

a non
-
JCR

data

stor
e

through the
JCR API

may encounter
names with characters
not allowed within
JCR names
.

To allow for this, a

JCR repository

should

expose

non
-
JCR
characters

as
private use Unicode code point

characters

according
to the
following mapping:

Non
-
JCR character

(
Unicode code point
)

P
rivate use

Unicode
code point

*

(U+002A)

U+F0
2A

/

(U+002F)

U+F02F

:

(
U+003A
)

U+F03A

[

(U+005B)

U+F05B


29

]

(U+005D)

U+F05D

|

(U+007C
)

U+F07C


This mapping
should

be used
when a JCR method returns a name
contain
ing

a

non
-
JCR character. The mapping
should

also be used
(in reverse) when a JCR method is called with a path or name
contain
in
g one of the six private use code points above
.

3.7

Properties

Every property is of one of the following types:



PropertyType.STRING



Propert
yType.BINARY



PropertyType.DATE



PropertyType.LONG



PropertyType.DOUBLE



PropertyType.BOOLEAN



PropertyType.NAME



PropertyType.PATH



PropertyType.REFERENCE



PropertyType.
WEAKREFERENCE



PropertyType.URI



PropertyType.DECIMAL

Methods are provided to read (in level 1)
and write (in level 2) the
values of properties to and from the appropriate native Java types
(i.e.
PropertyType.STRING

values can be read and written as
java.lang.String

objects,
PropertyType.LONG

values into Java
long

variables, and so on).

3.7.1

Multi
-
Value P
roperties

In some cases, a property may have more than one value
.
A
property that may have more than one value is referred to as a
multi
-
valued property (regardless of whether it currently has one or
more than one value).

Whether a particular property is a

multi
-
valued property is
governed by the property definition applicable to it, which is
determined by the node type of the property's parent node.

The values within a multi
-
valued property are ordered.


30

Accessing the values of such a property is done with
the method
Property.getValues
, which returns an array of
Value

objects that
contains the values in their prescribed order.

Accessing a multi
-
valued property with
Property.getValue
, or a
single
-
value property with
Property.getValues

will throw a
ValueFormat
Exception
.

The values stored within a multi
-
valued property are all of the same
type.

As with single
-
value properties, there is no such thing as a
null

value. If a value within a multi
-
value property is set to
null
, this is
equivalent to removing that valu
e from the value array. In such a
case the array is automatically compacted: shifting the indexes of
those values with indexes greater than that of the removed value
by
-
1.

Note that this
does

mean that a multi
-
value property can have
no
values

(i.e., be a
n empty array), whereas a single
-
value property
either has a (non
-
null) value or does not exist.

See
5.1.5

Adding and Writing Properties

for more details.

3.7.2

Property Types with Special Semantics

Five of the property types listed
above have special semantics:
NAME
,
PATH
,
REFERENCE
,
WEAKREFERENCE

and
URI
.

NAME

properties are used for storing strings that are namespace
-
qualified, such as the names of node types or the names of
repository items. A
NAME

property can be thought of as a
namespace
-
aware
STRING
. It is set like a string (for example,
setProperty("aNodeType", "nt:file"
, PropertyType.NAME
)
).
However, the prefix is automatically mapped to its current URI and
the value is stored using that full namespace URI. When the
property i
s later read the mapping is reversed and if the URI in
question has been remapped that remapping is reflected in the
returned value.

A
PATH

property represents a path in a workspace (either relative or
absolute) and therefore can also be used to refer to i
tems
elsewhere in the workspace. However, the
PATH

property does not
enforce referential integrity; in other words it can point to a
location where no item currently exists.
A property of type
PATH

can
be dereferenced by calling
Property.getNode or
Propert
y.getProperty
. These return the node or property in the
same workspace to which this
PATH

points.
Like a
NAME

property, a
PATH

is also namespace
-
aware in that its apparent value when read
will always reflect the current prefix to URI mapping.

A
REFERENCE

p
roperty is used to provide a named reference to a
node elsewhere in the workspace. The value of the property is the

31

referenceable identifier

of the node to which it refers.

Though every
node has an identifier, only referenceable nodes have referenceable
id
entifiers.

Consequently, only a referenceable node can be the
target of a
REFERENCE

property.
REFERENCE

properties have the
additional semantic feature of maintaining referential integrity by
preventing the removal of any node that is currently the target
of a
reference property. To remove a node that is the target of a
REFERENCE
, one must first remove the
REFERENCE
. The check for
referential integrity is done when an attempt is made to persist the
removal of a node (that is, either on
save
, or, if the chan
ge was
made within a transaction, on
commit
; in any case, the check is not
done immediately on
remove
). The method
s

Node.getReferences()

and
Node.getReferences(String name)

can be used to find

the

REFERENCE

properties that refer to a
particular node. T
he method
Node.setProperty(String name,
Node value)

can be used to set the value of a
REFERENCE

property
to the
referenceable identifier
of the specified node. A property of
type
REFERENCE

can be dereferenced by calling
Property.getNode
.
This returns the n
ode in the same workspace to which the property
points.

In versioning repositories the version storage is exposed in the
workspace tree as a protected subtree below
jcr:system/jcr:versionStorage

(see
6.4.2

Version Storage
).
Wit
hin this subtree, the referential integrity requirement is lifted for
REFERENCE

properties stored as part of the frozen state of a version
(see
6.4.3.9

Reference Properties within a Version
).

A
WEAKREFERENCE

property is identic
al to a
REFERENCE

property
except that it does not enforce referential integrity. A call to
Property.getNode

on a
WEAKREFERENCE

will throw an
ItemNotFoundException

if no node exists in the same workspace
with the specified
referenceable identifier
.

URI

pro
perties are identical to
STRING

properties, except that they
accept only values that that conform to the URI syntax.

3.7.3

No Null Values

Every property must have a value. The range of property states
does not include having a “null value”, or “no value”. Settin
g a
property to “null” is equivalent to removing that property. In the
case of multi
-
value properties, the setting of a particular value
within the array to null results in the removal of that value and the
compacting of the array. As a result it
is

possib
le to have a multi
-
value property with no values (an empty array). See
5.1.5

Adding
and Writing Properties
.

3.8

Node Types

Every node
must

have one and only one
primary node type
. The
primary node type defines the names, types and
other

32

characteristics of the properties and child nodes that a node is
allowed (or required) to have. Every node has a special property
called
jcr:primaryType

that records the name of its primary node
type.

In addition to its primary node type, a node
may

also have one or
more
mixin types
. These are node type definitions that can
mandate extra characteristics (i.e., more child nodes, properties
and their respective names and types) for a particular node in
addition to those enforced by its primary node type
. When a node is
assigned a mixin node type, it acquires a special multi
-
value
property called
jcr:mixinTypes

that records its mixin node types.

Level 1 of the specification provides methods for discovering the
node types of existing nodes, and for discove
ring and reading the
definitions of node types available in the repository.

Level 2 of the specification provides methods for assigning primary
and mixin node types to nodes.

The specification also defines an optional set of methods for
defining, creating
or managing primary or mixin node types.

Implementations are always free to enforce restrictions on the node
types allowed at particular locations in a workspace tree.

This specification also provides a set of predefined primary and
mixin node types; some
required and some optional. See
4.7

Node
Types
.

3.9

Identifiers

Every node has an identifier,
accessible through
Node.getIdentifier()
. A
n

identifier is an opaque string

whose

format is not defined by this specificat
ion

but which adheres to the
following constraints:



It

must be

unique
within a workspace. At
any particular
time, at
most one node in a workspace has a particular
identifier.



It

should be the most stable
identifier
available

to the

implementation.
For exam
ple, i
n some im
plementations
this
might be nothing more than the
node
path

itself
.
O
ther
implementations might
support

node identifiers
that are
partly or entirely
independent of the path
.


3.9.1

Referenceable
Identifiers

S
ome implementations

may support
referen
ceable nodes
. A
referenceable node must have a
referenceable identifier
,
which is
an identifier with the following
further constraints
:


33



It

must be

assigned
at the latest
when the node is
first
persiste
d
,

though it
may be assigned earlier, when the node
is
first created in transient storage in the session
.



It

is immutable during the lifetime of the node
, that is
,

until
the node is deleted though a
remove

operation.



In particular
,

it

is

immutable across
move

and
clone

operations
.

Note that non
-
referenceable i
dentifiers are
not

required to be immutable across these operations.



It is not immutable across
copy

operations
. T
his operation
results in the creation of a new node with a new
referenceable identifier
.

These are the minimum requirements for a referenc
eable identifier.
Implementations may choose to use identifiers that are even more
stable. For example, true UUIDs may be used by some repositories

(see

3.9.4

Constructing Referenceable Identifiers
, below)
.

3.9.2

Referenceable No
des

The concept of the referenceable node is foundational to many
features of the repository, including
multiple workspaces

and
versioning
.
A referenceable node has the following characteristics
:



A referenceable node must have the mixin type
mix:referencea
ble
.

It follows that a repository that supports
referenceable nodes must support the mixin type
mix:referenceable
.



The
mix:referenceable

type has the effect of enforcing, on
any node to which it is assigned, the presence of a property
called
jcr:uuid
. This

is a protected, auto
-
created, mandatory
property
.

I
t is created and
controlled

by the system and can
only be read (but not changed or deleted)
through the JCR API
.




The
jcr:uuid

property expose
s

the
referenceable identifier
of
its node
.
T
he property name
jcr:uuid

is used for compatibility
with JCR 1.
0
.

T
he identifier exposed need not be a true UUID,
though in some implementations it may be
.



The
jcr:uuid

property is created immediately upon the
creation of a referenceable node (either by mixin addition or,
if
the primary type inherits
mix:referenceable
, node creation).
However, since the assignment of identifiers in some
implementations may occur at persist
-
time, the value of
jcr:uuid

before the first
save

is not guaranteed to be the
identifier of the node (
see
3.9.7

When Identifiers are Assigned
)
.


34

3.9.3

Reference Properties

Being referenceable allows a node to be the target of a property of
type
REFERENCE

or
WEAKREFERENCE
. A
REFERENCE

or
WEAKREFERENCE

property stores the referencea
ble identifier of an existing node in
the same workspace.
REFERENCE

properties (but not
WEAKREFERENCE

properties) enforce referential integrity (see
4.2.9.4

Reference
). An exception to the referential integrity rule is m
ade for
REFERENCE

properties stored as part of frozen version state in the
version storage (see
6.4.3.9

Reference Properties within a Version
).

Reference properties are used to constructing named relations
between nodes in a wo
rkspace that cross
-
cut the path hierarchy.

The target of reference property is accessed though the
dereferencing method
Property.getNode
, called on the reference
property in question.

When the source subtree in a
copy

operation includes both a
reference pr
operty
P

and the node to which it refers
N

then
not only
does the new copy of the referenceable node (
N'
) get a new
identifier (as discussed above in
3.9.2

Referenceable Nodes
)

but
the new copy of the reference property (
P'
) is

changed so that it
points to
N'
, thus preserving the reference within the subtree.

3.9.4

Constructing
Referenceable
Identifiers

As mentioned, r
eferenceable identifiers
must meet certain minimal
criteria, but implementations are free to exceed those criteria. Mo
st
implementations will probably use on
e

of two possible types of
referenceable identifiers:



A true universally unique identifier (UUID). Such an
identifier is stable across
move

(within a workspace),
clone

(to another workspace) and export and import (to
or from a
workspace in another repository).



A

repository
-
assigned identifier that stays stable across
move

and
clone
, but which might not be universally unique, and
therefore would not be stable across export and import.

3.9.5

Hybrid and Other

Non
-
referenceable
Identifiers

The non
-
referenceable nodes will be those for which it is not
practical to construct an identifier that meets the requirements of
referenceability. Nonetheless,
since
every node needs an identifier
,
the repository must be able to construct one
for every node.

One possible method is to define a identifier for non
-
referenceable
nodes
is the
hybrid identifier
, defined
as follows:



If the node has at least one referenceable ancestor, its
identifier is the pair consisting of the identifier of its nea
rest

35

referenceable ancestor and its relative path from that
ancestor.



If the node has no referenceable ancestors its identifier is its
absolute path.

Other possibly implementations
of
non
-
referenceable
identifiers
exist as well.

3.9.6

Restricting Referenceable N
odes

Some implementations may allow (or require) every node to be
referenceable. In other cases, especially where JCR is implemented
on top of an existing datastore, the provision of referenceable
identifiers for every node may be impractical.

For example
, a JCR view of a file system store of XML documents
might expose not only the file hierarchy but also the internal
structure of each XML document as a node/property structure. In
such a case providing a referenceable identifier for a node
representing a X
ML document might be practical while providing a
such an identifier for nodes representing individual XML elements
inside the document might not be
.

To handle these cases, implementations can take advantage of
their general discretion over node type as
signment to enforce
restrictions over which nodes are allowed to have the
mix:referenceable

node type.

3.9.7

When
Identifiers

are Assigned

In some client
-
server implementations the assignment of a
permanent
identifier

may be done on the server. In these cases it

is
not practical for a newly created referenceable node to be given a
identifier

upon creation. Rather, it makes more sense for the
identifier

to be assigned upon
save

of that node. In such cases a
“dummy
identifier
” may be assigned on creation of a new n
ode
while the real
identifier

assignment takes place later, upon
save
.
Applications should not, therefore, rely on the
identifier

of a node
before that node is saved for the first time.

3.10

Workspaces

A content repository is composed of a number of
workspaces
.

Each
workspace contains a single rooted tree of items. In the simplest
case a repository will consist of just one workspace. In more
complex cases a repository will consist of more than one
workspace.

3.10.1

Single Workspace Repositories

A repository with only a

single workspace consists of a single tree
of nodes and properties. The example at the beginning of this

36

section (
3

The Repository Model
) describes a single workspace
repository.

Since a given workspace contains at most one no
de with a given
identifier
, in this case, there is at most one node with a given
identifier

in the repository as a whole
.

The following diagram depicts a single workspace repository:


37














The small circles represent nodes. The arrows point from p
arent to
child and are labeled with the name of the child. The name of the
root node is actually the empty string though, for clarity, it is
indicated here with the string “
[root]
”. The
symbols

within the
nodes represent the
identifiers

of the nodes. For e
xample, the
identifier

of the root node
/

is
00

and the
identifier

of
/a/d

is
03
.
All
the nodes apart from
/a/c

are
referenceable

and so have path
independent identifiers. /a/c however, is non
-
referenceable and (in
this example)

has a hybrid identifier:

t
h
e referenceable identifier of
its nearest referenceable ancestor, and its relative path from that
node.

3.10.2

Multiple Workspaces and Corresponding Nodes

In repositories that have multiple workspaces, a node in one
workspace may have
corresponding nodes

in other

workspaces. A
node's corresponding nodes are those with the same

identifier

(referenceable or otherwise)
.

In r
epositor