]> git.argeo.org Git - lgpl/argeo-commons.git/blob - WorkspaceFileStore.java
e8f24c9de8b44ebe8ba68500c314469ff52593f5
[lgpl/argeo-commons.git] / WorkspaceFileStore.java
1 package org.argeo.jcr.fs;
2
3 import java.io.IOException;
4 import java.nio.file.FileStore;
5 import java.nio.file.attribute.FileAttributeView;
6 import java.nio.file.attribute.FileStoreAttributeView;
7 import java.util.Arrays;
8
9 import javax.jcr.Node;
10 import javax.jcr.RepositoryException;
11 import javax.jcr.Session;
12 import javax.jcr.Workspace;
13
14 import org.argeo.api.gcr.fs.AbstractFsStore;
15 import org.argeo.jcr.JcrUtils;
16
17 /** A {@link FileStore} implementation based on JCR {@link Workspace}. */
18 public class WorkspaceFileStore extends AbstractFsStore {
19 private final String mountPath;
20 private final Workspace workspace;
21 private final String workspaceName;
22 private final int mountDepth;
23
24 public WorkspaceFileStore(String mountPath, Workspace workspace) {
25 if ("/".equals(mountPath) || "".equals(mountPath))
26 throw new IllegalArgumentException(
27 "Mount path '" + mountPath + "' is unsupported, use null for the base file store");
28 if (mountPath != null && !mountPath.startsWith(JcrPath.separator))
29 throw new IllegalArgumentException("Mount path '" + mountPath + "' cannot end with /");
30 if (mountPath != null && mountPath.endsWith(JcrPath.separator))
31 throw new IllegalArgumentException("Mount path '" + mountPath + "' cannot end with /");
32 this.mountPath = mountPath;
33 if (mountPath == null)
34 mountDepth = 0;
35 else {
36 mountDepth = mountPath.split(JcrPath.separator).length - 1;
37 }
38 this.workspace = workspace;
39 this.workspaceName = workspace.getName();
40 }
41
42 public void close() {
43 JcrUtils.logoutQuietly(workspace.getSession());
44 }
45
46 @Override
47 public String name() {
48 return workspace.getName();
49 }
50
51 @Override
52 public String type() {
53 return "workspace";
54 }
55
56 @Override
57 public boolean isReadOnly() {
58 return false;
59 }
60
61 @Override
62 public long getTotalSpace() throws IOException {
63 return 0;
64 }
65
66 @Override
67 public long getUsableSpace() throws IOException {
68 return 0;
69 }
70
71 @Override
72 public long getUnallocatedSpace() throws IOException {
73 return 0;
74 }
75
76 @Override
77 public boolean supportsFileAttributeView(Class<? extends FileAttributeView> type) {
78 return false;
79 }
80
81 @Override
82 public boolean supportsFileAttributeView(String name) {
83 return false;
84 }
85
86 @Override
87 public <V extends FileStoreAttributeView> V getFileStoreAttributeView(Class<V> type) {
88 return null;
89 }
90
91 @Override
92 public Object getAttribute(String attribute) throws IOException {
93 return workspace.getSession().getRepository().getDescriptor(attribute);
94 }
95
96 public Workspace getWorkspace() {
97 return workspace;
98 }
99
100 public String toFsPath(Node node) throws RepositoryException {
101 String nodeWorkspaceName = node.getSession().getWorkspace().getName();
102 if (!nodeWorkspaceName.equals(workspace.getName()))
103 throw new IllegalArgumentException("Icompatible " + node + " from workspace '" + nodeWorkspaceName
104 + "' in file store '" + workspace.getName() + "'");
105 return mountPath == null ? node.getPath() : mountPath + node.getPath();
106 }
107
108 public boolean isBase() {
109 return mountPath == null;
110 }
111
112 Node toNode(String[] fullPath) throws RepositoryException {
113 String jcrPath = toJcrPath(fullPath);
114 Session session = workspace.getSession();
115 if (!session.itemExists(jcrPath))
116 return null;
117 Node node = session.getNode(jcrPath);
118 return node;
119 }
120
121 String toJcrPath(String fsPath) {
122 if (fsPath.length() == 1)
123 return toJcrPath((String[]) null);// root
124 String[] arr = fsPath.substring(1).split("/");
125 // if (arr.length == 0 || (arr.length == 1 && arr[0].equals("")))
126 // return toJcrPath((String[]) null);// root
127 // else
128 return toJcrPath(arr);
129 }
130
131 private String toJcrPath(String[] path) {
132 if (path == null)
133 return "/";
134 if (path.length < mountDepth)
135 throw new IllegalArgumentException(
136 "Path " + Arrays.asList(path) + " is no compatible with mount " + mountPath);
137
138 if (!isBase()) {
139 // check mount compatibility
140 StringBuilder mount = new StringBuilder();
141 mount.append('/');
142 for (int i = 0; i < mountDepth; i++) {
143 if (i != 0)
144 mount.append('/');
145 mount.append(Text.escapeIllegalJcrChars(path[i]));
146 }
147 if (!mountPath.equals(mount.toString()))
148 throw new IllegalArgumentException(
149 "Path " + Arrays.asList(path) + " is no compatible with mount " + mountPath);
150 }
151
152 StringBuilder sb = new StringBuilder();
153 sb.append('/');
154 for (int i = mountDepth; i < path.length; i++) {
155 if (i != mountDepth)
156 sb.append('/');
157 sb.append(Text.escapeIllegalJcrChars(path[i]));
158 }
159 return sb.toString();
160 }
161
162 public String getMountPath() {
163 return mountPath;
164 }
165
166 public String getWorkspaceName() {
167 return workspaceName;
168 }
169
170 public int getMountDepth() {
171 return mountDepth;
172 }
173
174 @Override
175 public int hashCode() {
176 return workspaceName.hashCode();
177 }
178
179 @Override
180 public boolean equals(Object obj) {
181 if (!(obj instanceof WorkspaceFileStore))
182 return false;
183 WorkspaceFileStore other = (WorkspaceFileStore) obj;
184 return workspaceName.equals(other.workspaceName);
185 }
186
187 @Override
188 public String toString() {
189 return "WorkspaceFileStore " + workspaceName;
190 }
191
192 }