mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
DOM stubs: stub serialization decoupled from PSI
This commit is contained in:
@@ -0,0 +1,35 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
package com.intellij.psi.stubs;
|
||||
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
/**
|
||||
* @author Dmitry Avdeev
|
||||
* Date: 8/2/12
|
||||
*/
|
||||
public interface ObjectStubSerializer<T extends Stub, P extends Stub> {
|
||||
@NonNls
|
||||
String getExternalId();
|
||||
|
||||
void serialize(T stub, StubOutputStream dataStream) throws IOException;
|
||||
T deserialize(StubInputStream dataStream, final P parentStub) throws IOException;
|
||||
|
||||
void indexStub(T stub, IndexSink sink);
|
||||
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
package com.intellij.psi.stubs;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author Dmitry Avdeev
|
||||
* Date: 8/2/12
|
||||
*/
|
||||
public interface Stub {
|
||||
|
||||
Stub getParentStub();
|
||||
List<? extends Stub> getChildrenStubs();
|
||||
ObjectStubSerializer getStubType();
|
||||
|
||||
}
|
||||
@@ -27,7 +27,7 @@ import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public interface StubElement<T extends PsiElement> {
|
||||
public interface StubElement<T extends PsiElement> extends Stub {
|
||||
IStubElementType getStubType();
|
||||
StubElement getParentStub();
|
||||
List<StubElement> getChildrenStubs();
|
||||
|
||||
@@ -42,36 +42,36 @@ import java.util.concurrent.locks.Lock;
|
||||
public class StubSerializationHelper {
|
||||
private AbstractStringEnumerator myNameStorage;
|
||||
|
||||
protected final TIntObjectHashMap<StubSerializer<? extends StubElement>> myIdToSerializer = new TIntObjectHashMap<StubSerializer<? extends StubElement>>();
|
||||
protected final TObjectIntHashMap<StubSerializer<? extends StubElement>> mySerializerToId = new TObjectIntHashMap<StubSerializer<? extends StubElement>>();
|
||||
protected final TIntObjectHashMap<ObjectStubSerializer> myIdToSerializer = new TIntObjectHashMap<ObjectStubSerializer>();
|
||||
protected final TObjectIntHashMap<ObjectStubSerializer> mySerializerToId = new TObjectIntHashMap<ObjectStubSerializer>();
|
||||
|
||||
public StubSerializationHelper(AbstractStringEnumerator nameStorage) {
|
||||
myNameStorage = nameStorage;
|
||||
}
|
||||
|
||||
public void assignId(@NotNull final StubSerializer<? extends StubElement> serializer) throws IOException {
|
||||
public void assignId(@NotNull final ObjectStubSerializer serializer) throws IOException {
|
||||
final int id = persistentId(serializer);
|
||||
final StubSerializer old = myIdToSerializer.put(id, serializer);
|
||||
final ObjectStubSerializer old = myIdToSerializer.put(id, serializer);
|
||||
assert old == null : "ID: " + serializer.getExternalId() + " is not unique; Already registered serializer with this ID: " + old.getClass().getName();
|
||||
|
||||
final int oldId = mySerializerToId.put(serializer, id);
|
||||
assert oldId == 0 : "Serializer " + serializer + " is already registered; Old ID:" + oldId;
|
||||
}
|
||||
|
||||
private int persistentId(@NotNull final StubSerializer<? extends StubElement> serializer) throws IOException {
|
||||
private int persistentId(@NotNull final ObjectStubSerializer serializer) throws IOException {
|
||||
if (myNameStorage == null) {
|
||||
throw new IOException("SerializationManager's name storage failed to initialize");
|
||||
}
|
||||
return myNameStorage.enumerate(serializer.getExternalId());
|
||||
}
|
||||
|
||||
private void doSerialize(final StubElement rootStub, final StubOutputStream stream) throws IOException {
|
||||
final StubSerializer serializer = StubSerializationUtil.getSerializer(rootStub);
|
||||
private void doSerialize(final Stub rootStub, final StubOutputStream stream) throws IOException {
|
||||
final ObjectStubSerializer serializer = StubSerializationUtil.getSerializer(rootStub);
|
||||
|
||||
DataInputOutputUtil.writeINT(stream, getClassId(serializer));
|
||||
serializer.serialize(rootStub, stream);
|
||||
|
||||
final List<StubElement> children = rootStub.getChildrenStubs();
|
||||
final List<? extends Stub> children = rootStub.getChildrenStubs();
|
||||
final int childrenSize = children.size();
|
||||
DataInputOutputUtil.writeINT(stream, childrenSize);
|
||||
for (int i = 0; i < childrenSize; ++i) {
|
||||
@@ -79,7 +79,7 @@ public class StubSerializationHelper {
|
||||
}
|
||||
}
|
||||
|
||||
public void serialize(StubElement rootStub, OutputStream stream) throws IOException {
|
||||
public void serialize(Stub rootStub, OutputStream stream) throws IOException {
|
||||
BufferExposingByteArrayOutputStream out = new BufferExposingByteArrayOutputStream();
|
||||
FileLocalStringEnumerator storage = new FileLocalStringEnumerator();
|
||||
StubOutputStream stubOutputStream = new StubOutputStream(out, storage);
|
||||
@@ -94,7 +94,7 @@ public class StubSerializationHelper {
|
||||
resultStream.write(out.getInternalBuffer(), 0, out.size());
|
||||
}
|
||||
|
||||
private int getClassId(final StubSerializer serializer) {
|
||||
private int getClassId(final ObjectStubSerializer serializer) {
|
||||
final int idValue = mySerializerToId.get(serializer);
|
||||
assert idValue != 0: "No ID found for serializer " + LogUtil.objectAndClass(serializer);
|
||||
return idValue;
|
||||
@@ -152,7 +152,7 @@ public class StubSerializationHelper {
|
||||
|
||||
private final RecentStringInterner myStringInterner = new RecentStringInterner(8192);
|
||||
|
||||
public StubElement deserialize(InputStream stream) throws IOException {
|
||||
public Stub deserialize(InputStream stream) throws IOException {
|
||||
FileLocalStringEnumerator storage = new FileLocalStringEnumerator();
|
||||
StubInputStream inputStream = new StubInputStream(stream, storage);
|
||||
final int size = DataInputOutputUtil.readINT(inputStream);
|
||||
@@ -168,13 +168,13 @@ public class StubSerializationHelper {
|
||||
return deserialize(inputStream, null);
|
||||
}
|
||||
|
||||
private StubElement deserialize(StubInputStream stream, StubElement parentStub) throws IOException {
|
||||
private Stub deserialize(StubInputStream stream, Stub parentStub) throws IOException {
|
||||
final int id = DataInputOutputUtil.readINT(stream);
|
||||
final StubSerializer serializer = getClassById(id);
|
||||
final ObjectStubSerializer serializer = getClassById(id);
|
||||
|
||||
assert serializer != null : "No serializer registered for stub: ID=" + id + "; parent stub class=" + (parentStub != null? parentStub.getClass().getName() : "null");
|
||||
|
||||
StubElement stub = serializer.deserialize(stream, parentStub);
|
||||
Stub stub = serializer.deserialize(stream, parentStub);
|
||||
int childCount = DataInputOutputUtil.readINT(stream);
|
||||
for (int i = 0; i < childCount; i++) {
|
||||
deserialize(stream, stub);
|
||||
@@ -183,7 +183,7 @@ public class StubSerializationHelper {
|
||||
}
|
||||
|
||||
|
||||
private StubSerializer getClassById(int id) {
|
||||
private ObjectStubSerializer getClassById(int id) {
|
||||
return myIdToSerializer.get(id);
|
||||
}
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ package com.intellij.psi.stubs;
|
||||
public abstract class StubSerializationUtil {
|
||||
private StubSerializationUtil() {}
|
||||
|
||||
public static StubSerializer getSerializer(StubElement rootStub) {
|
||||
public static ObjectStubSerializer getSerializer(Stub rootStub) {
|
||||
if (rootStub instanceof PsiFileStub) {
|
||||
final PsiFileStub fileStub = (PsiFileStub)rootStub;
|
||||
return fileStub.getType();
|
||||
|
||||
@@ -22,7 +22,7 @@ import java.io.IOException;
|
||||
/*
|
||||
* @author max
|
||||
*/
|
||||
public interface StubSerializer<T extends StubElement> {
|
||||
public interface StubSerializer<T extends StubElement> extends ObjectStubSerializer<T, StubElement> {
|
||||
@NonNls
|
||||
String getExternalId();
|
||||
|
||||
|
||||
@@ -45,7 +45,7 @@ public class CoreStubTreeLoader extends StubTreeLoader {
|
||||
try {
|
||||
final FileContent fc = new FileContentImpl(vFile, vFile.contentsToByteArray());
|
||||
fc.putUserData(IndexingDataKeys.PROJECT, project);
|
||||
final StubElement element = StubTreeBuilder.buildStubTree(fc);
|
||||
final Stub element = StubTreeBuilder.buildStubTree(fc);
|
||||
if (element instanceof PsiFileStub) {
|
||||
return new StubTree((PsiFileStub)element);
|
||||
}
|
||||
|
||||
@@ -29,14 +29,14 @@ import com.intellij.util.indexing.SubstitutedFileType;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
public class StubTreeBuilder {
|
||||
private static final Key<StubElement> stubElementKey = Key.create("stub.tree.for.file.content");
|
||||
private static final Key<Stub> stubElementKey = Key.create("stub.tree.for.file.content");
|
||||
|
||||
private StubTreeBuilder() {
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static StubElement buildStubTree(final FileContent inputData) {
|
||||
StubElement data = inputData.getUserData(stubElementKey);
|
||||
public static Stub buildStubTree(final FileContent inputData) {
|
||||
Stub data = inputData.getUserData(stubElementKey);
|
||||
if (data != null) return data;
|
||||
|
||||
//noinspection SynchronizationOnLocalVariableOrMethodParameter
|
||||
|
||||
@@ -27,9 +27,9 @@ public abstract class SerializationManagerEx extends SerializationManager {
|
||||
return (SerializationManagerEx) SerializationManager.getInstance();
|
||||
}
|
||||
|
||||
public abstract void serialize(StubElement rootStub, OutputStream stream);
|
||||
public abstract void serialize(Stub rootStub, OutputStream stream);
|
||||
|
||||
public abstract StubElement deserialize(InputStream stream);
|
||||
public abstract Stub deserialize(InputStream stream);
|
||||
|
||||
public abstract boolean isNameStorageCorrupted();
|
||||
|
||||
|
||||
@@ -146,7 +146,7 @@ public class SerializationManagerImpl extends SerializationManagerEx implements
|
||||
|
||||
|
||||
|
||||
public void serialize(StubElement rootStub, OutputStream stream) {
|
||||
public void serialize(Stub rootStub, OutputStream stream) {
|
||||
initSerializers();
|
||||
try {
|
||||
myStubSerializationHelper.serialize(rootStub, stream);
|
||||
@@ -158,7 +158,7 @@ public class SerializationManagerImpl extends SerializationManagerEx implements
|
||||
}
|
||||
|
||||
|
||||
public StubElement deserialize(InputStream stream) {
|
||||
public Stub deserialize(InputStream stream) {
|
||||
initSerializers();
|
||||
|
||||
try {
|
||||
|
||||
@@ -30,9 +30,9 @@ import java.io.IOException;
|
||||
public class SerializedStubTree {
|
||||
private final byte[] myBytes;
|
||||
private final int myLength;
|
||||
private StubElement myStubElement;
|
||||
private Stub myStubElement;
|
||||
|
||||
public SerializedStubTree(final byte[] bytes, int length, @Nullable StubElement stubElement) {
|
||||
public SerializedStubTree(final byte[] bytes, int length, @Nullable Stub stubElement) {
|
||||
myBytes = bytes;
|
||||
myLength = length;
|
||||
myStubElement = stubElement;
|
||||
@@ -48,8 +48,8 @@ public class SerializedStubTree {
|
||||
}
|
||||
|
||||
// willIndexStub is one time optimization hint, once can safely pass false
|
||||
public StubElement getStub(boolean willIndexStub) {
|
||||
StubElement stubElement = myStubElement;
|
||||
public Stub getStub(boolean willIndexStub) {
|
||||
Stub stubElement = myStubElement;
|
||||
if (stubElement != null) {
|
||||
// not null myStubElement means we just built SerializedStubTree for indexing,
|
||||
// if we request stub for indexing we can safely use it
|
||||
|
||||
@@ -60,7 +60,7 @@ public class StubTreeLoaderImpl extends StubTreeLoader {
|
||||
}
|
||||
psiFile.putUserData(PsiFileImpl.BUILDING_STUB, true);
|
||||
}
|
||||
StubElement element;
|
||||
Stub element;
|
||||
try {
|
||||
element = StubTreeBuilder.buildStubTree(fc);
|
||||
}
|
||||
@@ -94,7 +94,7 @@ public class StubTreeLoaderImpl extends StubTreeLoader {
|
||||
final int size = datas.size();
|
||||
|
||||
if (size == 1) {
|
||||
StubElement stub = datas.get(0).getStub(false);
|
||||
Stub stub = datas.get(0).getStub(false);
|
||||
return new StubTree((PsiFileStub)stub);
|
||||
}
|
||||
else if (size != 0) {
|
||||
|
||||
@@ -118,7 +118,7 @@ public class StubUpdatingIndex extends CustomImplementationFileBasedIndexExtensi
|
||||
ApplicationManager.getApplication().runReadAction(new Runnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
final StubElement rootStub = StubTreeBuilder.buildStubTree(inputData);
|
||||
final Stub rootStub = StubTreeBuilder.buildStubTree(inputData);
|
||||
if (rootStub == null) return;
|
||||
|
||||
final BufferExposingByteArrayOutputStream bytes = new BufferExposingByteArrayOutputStream();
|
||||
|
||||
@@ -0,0 +1,23 @@
|
||||
/*
|
||||
* Copyright 2000-2012 JetBrains s.r.o.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
package com.intellij.util.xml.stubs;
|
||||
|
||||
/**
|
||||
* @author Dmitry Avdeev
|
||||
* Date: 8/2/12
|
||||
*/
|
||||
public class DomStubElement {
|
||||
}
|
||||
Reference in New Issue
Block a user