| Summary: | UI freeze during expanding EJB project | ||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Product: | [WebTools] WTP Java EE Tools | Reporter: | Krzysztof Daniel <krzysztof.daniel> | ||||||||||
| Component: | jst.j2ee | Assignee: | Dimitar Giormov <dimitar.giormov> | ||||||||||
| Status: | RESOLVED FIXED | QA Contact: | Chuck Bridgham <cbridgha> | ||||||||||
| Severity: | enhancement | ||||||||||||
| Priority: | P3 | CC: | ccc, kaloyan, krzysztof.daniel, Olivier_Thomann | ||||||||||
| Version: | 3.2 | Flags: | cbridgha:
review+
|
||||||||||
| Target Milestone: | 3.3.2 | ||||||||||||
| Hardware: | PC | ||||||||||||
| OS: | Windows XP | ||||||||||||
| Whiteboard: | |||||||||||||
| Bug Depends on: | |||||||||||||
| Bug Blocks: | 329966, 352841 | ||||||||||||
| Attachments: |
|
||||||||||||
|
Description
Krzysztof Daniel
Assigning to Kaloyan for initial investigation - SAP contributed the Ejb3ContentProvider code. Christopher, to clarify, which version of WTP are you reporting this against? I have reproduced this with 3.7M2a, but it is a problem in 3.6, too. Eclipse 3.6 corresponds to WTP 3.2, so I am setting the version to 3.2. Created attachment 181845 [details]
Dirty, ugly hack which works only for one project and has a lot of errors
Some initial work. Further advice is welcome.
Christopher, thank you for the comprehensive bug report. Dimitar, you are more familiar with the EJB 3 model than me. Could you take care? Created attachment 181931 [details]
Much better patch
It works. Only the actions "New bean" throw exception, but UI is no longer blocked.
Thanks Christopher, What I can do about this is to proceed in the same manner as in J2ee 1.4 models, where an animation shows that the model is being loaded and the tree is expanded afterwords. But trying to simulate the same scenario on my pc having 100 beans (80 session, 20 MDb's) does not brought performance degradation. The tree opens like always (under a second) I tried and brought some more annotations and EJB injections, but it kept working ok. It could be that some referenced projects or network latency can cause this. (how I tested is trying to open the project and DD tree node right after the eclipse is started, so nothing is cached) Can you share some project(s) that has this performance degradation, it could be that a certain property takes a lot of time to be processed. To summarize :) I will make the loading of the model asynchronous. I will start with your new patch. I need your help to figure out where these long running operations occur. P.S. attach binary files such as images separately. Having them in a patch makes them useless. Unfortunately I cannot share the project - I will try to build a minimal test case. Here is javacore: String.lastIndexOf(int, int) line: 856 String.lastIndexOf(int) line: 835 NameLookup.seekTypesInSourcePackage(String, IPackageFragment, int, boolean, String, int, IJavaElementRequestor) line: 1078 NameLookup.seekTypes(String, IPackageFragment, boolean, int, IJavaElementRequestor) line: 987 NameLookup.findType(String, IPackageFragment, boolean, int) line: 776 NameLookup.findType(String, String, boolean, int, boolean, boolean, boolean, IProgressMonitor) line: 660 NameLookup.findType(String, String, boolean, int, boolean) line: 619 SearchableEnvironment.find(String, String) line: 101 SearchableEnvironment.findType(char[], char[][]) line: 287 LookupEnvironment.askForType(PackageBinding, char[]) line: 132 PackageBinding.getTypeOrPackage(char[]) line: 183 ClassScope(Scope).getTypeOrPackage(char[], int, boolean) line: 2642 ClassScope(Scope).getType(char[]) line: 2359 SingleTypeReference.getTypeBinding(Scope) line: 44 SingleTypeReference(TypeReference).internalResolveType(Scope) line: 131 SingleTypeReference(TypeReference).resolveType(ClassScope) line: 207 SingleTypeReference(TypeReference).resolveTypeArgument(ClassScope, ReferenceBinding, int) line: 225 ParameterizedQualifiedTypeReference.internalResolveType(Scope, boolean) line: 213 ParameterizedQualifiedTypeReference.resolveType(ClassScope) line: 341 ParameterizedQualifiedTypeReference(TypeReference).resolveSuperType(ClassScope) line: 185 ClassScope.findSupertype(TypeReference) line: 1213 ClassScope.connectSuperInterfaces() line: 980 ClassScope.connectTypeHierarchy() line: 1034 CompilationUnitScope.connectTypeHierarchy() line: 299 LookupEnvironment.completeTypeBindings(CompilationUnitDeclaration, boolean) line: 258 SelectionEngine(Engine).accept(ISourceType[], PackageBinding, AccessRestriction) line: 99 LookupEnvironment.askForType(PackageBinding, char[]) line: 144 PackageBinding.getTypeOrPackage(char[]) line: 183 ClassScope(Scope).getTypeOrPackage(char[], int, boolean) line: 2642 ClassScope(Scope).getType(char[]) line: 2359 SingleTypeReference.getTypeBinding(Scope) line: 44 SingleTypeReference(TypeReference).internalResolveType(Scope) line: 131 SingleTypeReference(TypeReference).resolveType(ClassScope) line: 207 SingleTypeReference(TypeReference).resolveTypeArgument(ClassScope, ReferenceBinding, int) line: 225 ParameterizedQualifiedTypeReference.internalResolveType(Scope, boolean) line: 213 ParameterizedQualifiedTypeReference.resolveType(ClassScope) line: 341 ParameterizedQualifiedTypeReference(TypeReference).resolveSuperType(ClassScope) line: 185 ClassScope.findSupertype(TypeReference) line: 1213 ClassScope.connectSuperInterfaces() line: 980 ClassScope.connectTypeHierarchy() line: 1034 CompilationUnitScope.connectTypeHierarchy() line: 299 LookupEnvironment.completeTypeBindings(CompilationUnitDeclaration, boolean) line: 258 SelectionEngine(Engine).accept(ISourceType[], PackageBinding, AccessRestriction) line: 99 LookupEnvironment.askForType(PackageBinding, char[]) line: 144 PackageBinding.getTypeOrPackage(char[]) line: 183 ClassScope(Scope).getTypeOrPackage(char[], int, boolean) line: 2642 ClassScope(Scope).getType(char[]) line: 2359 SingleTypeReference.getTypeBinding(Scope) line: 44 SingleTypeReference(TypeReference).internalResolveType(Scope) line: 131 SingleTypeReference(TypeReference).resolveType(ClassScope) line: 207 SingleTypeReference(TypeReference).resolveTypeArgument(ClassScope, ReferenceBinding, int) line: 225 ParameterizedQualifiedTypeReference.internalResolveType(Scope, boolean) line: 213 ParameterizedQualifiedTypeReference.resolveType(ClassScope) line: 341 ParameterizedQualifiedTypeReference(TypeReference).resolveSuperType(ClassScope) line: 185 ClassScope.findSupertype(TypeReference) line: 1213 ClassScope.connectSuperInterfaces() line: 980 ClassScope.connectTypeHierarchy() line: 1034 CompilationUnitScope.connectTypeHierarchy() line: 299 LookupEnvironment.completeTypeBindings(CompilationUnitDeclaration, boolean) line: 258 SelectionEngine(Engine).accept(ISourceType[], PackageBinding, AccessRestriction) line: 99 LookupEnvironment.askForType(PackageBinding, char[]) line: 144 PackageBinding.getTypeOrPackage(char[]) line: 183 ClassScope(Scope).getTypeOrPackage(char[], int, boolean) line: 2642 ClassScope(Scope).getType(char[]) line: 2359 SingleTypeReference.getTypeBinding(Scope) line: 44 SingleTypeReference(TypeReference).internalResolveType(Scope) line: 131 SingleTypeReference(TypeReference).resolveType(ClassScope) line: 207 SingleTypeReference(TypeReference).resolveTypeArgument(ClassScope, ReferenceBinding, int) line: 225 ParameterizedQualifiedTypeReference.internalResolveType(Scope, boolean) line: 213 ParameterizedQualifiedTypeReference.resolveType(ClassScope) line: 341 ParameterizedQualifiedTypeReference(TypeReference).resolveSuperType(ClassScope) line: 185 ClassScope.findSupertype(TypeReference) line: 1213 ClassScope.connectSuperInterfaces() line: 980 ClassScope.connectTypeHierarchy() line: 1034 CompilationUnitScope.connectTypeHierarchy() line: 299 LookupEnvironment.completeTypeBindings(CompilationUnitDeclaration, boolean) line: 258 SelectionEngine(Engine).accept(ISourceType[], PackageBinding, AccessRestriction) line: 99 LookupEnvironment.askForType(PackageBinding, char[]) line: 144 PackageBinding.getTypeOrPackage(char[]) line: 183 ClassScope(Scope).getTypeOrPackage(char[], int, boolean) line: 2642 ClassScope(Scope).getType(char[]) line: 2359 SingleTypeReference.getTypeBinding(Scope) line: 44 SingleTypeReference(TypeReference).internalResolveType(Scope) line: 131 SingleTypeReference(TypeReference).resolveType(ClassScope) line: 207 SingleTypeReference(TypeReference).resolveTypeArgument(ClassScope, ReferenceBinding, int) line: 225 ParameterizedQualifiedTypeReference.internalResolveType(Scope, boolean) line: 213 ParameterizedQualifiedTypeReference.resolveType(ClassScope) line: 341 ParameterizedQualifiedTypeReference(TypeReference).resolveSuperType(ClassScope) line: 185 ClassScope.findSupertype(TypeReference) line: 1213 ClassScope.connectSuperInterfaces() line: 980 ClassScope.connectTypeHierarchy() line: 1034 CompilationUnitScope.connectTypeHierarchy() line: 299 LookupEnvironment.completeTypeBindings(CompilationUnitDeclaration, boolean) line: 258 SelectionEngine(Engine).accept(ISourceType[], PackageBinding, AccessRestriction) line: 99 LookupEnvironment.askForType(PackageBinding, char[]) line: 144 PackageBinding.getTypeOrPackage(char[]) line: 183 CompilationUnitScope.findImport(char[][], int) line: 486 CompilationUnitScope.findSingleImport(char[][], int, boolean) line: 540 CompilationUnitScope.faultInImports() line: 368 CompilationUnitScope.faultInTypes() line: 465 SelectionEngine.selectType(char[], IType) line: 1425 SourceType(NamedMember).resolveType(String, WorkingCopyOwner) line: 292 SourceType(NamedMember).resolveType(String) line: 245 EjbAnnotationFactory.processImplementedInterfaces(SessionBean, IType, Collection<IType>, IProgressMonitor) line: 331 EjbAnnotationFactory.createSession(Result, SessionType, IAnnotation, IType) line: 201 EjbAnnotationFactory.processStatelessBean(Result, IAnnotation, IType) line: 141 EjbAnnotationFactory.createJavaeeObject(IType) line: 119 EJBAnnotationReader.analyzeUnitForBean(ICompilationUnit) line: 290 EJBAnnotationReader.loadModel() line: 225 EJBAnnotationReader(AbstractAnnotationModelProvider<T>).getConcreteModel() line: 106 EJBAnnotationReader(AbstractAnnotationModelProvider<T>).getModelObject() line: 122 EJB3MergedModelProvider(AbstractMergedModelProvider<T>).loadProviders() line: 242 AbstractMergedModelProvider<T>.access$1(AbstractMergedModelProvider) line: 235 AbstractMergedModelProvider$LoadModelsWorkspaceRunnable.run(IProgressMonitor) line: 255 Workspace.run(IWorkspaceRunnable, ISchedulingRule, int, IProgressMonitor) line: 1975 EJB3MergedModelProvider(AbstractMergedModelProvider<T>).loadModel() line: 229 EJB3MergedModelProvider(AbstractMergedModelProvider<T>).getMergedModel() line: 213 EJB3MergedModelProvider(AbstractMergedModelProvider<T>).getModelObject() line: 133 Ejb3ContentProvider$LoadContentProviderJob.run(IProgressMonitor) line: 275 Worker.run() line: 54 Alternative approach maybe to dump annotations model to file, so EJBAnnotationReader#loadModel could load it from file, and then, in the background, process diffs, if any. The most expensive operations should be the building of the annotation model itself. All operation afterwords are trivial. From your stacktrace it currently resolves a type. Which is one of the expensive operations we do. Can you try to profile the operation. this article can help you how if you haven't done it till now: http://www.eclipse.org/articles/Article-TPTP-Profiling-Tool/tptpProfilingArticle.html Christopher the 3.2.3 release draws near, if you can provide some junit or profile results, on which I can work on it will be great. The impact of such performance degradation could be huge. We can easily fix the tree, but wizards for creating an artifact calls these same methods for the purpose of validation on every keystroke for example. I am sorry, my priorities has been shifted and I am no longer able to work on this issue. The problem was visible only during the first model loading after restart, so you should not be worried about validators (I also bet that there is some kind of caching during type resolution). It looks like the number of beans is not the only factor - those beans had also very high stack of inheritance. OK shifting it to indigo. Where the async loading will occur. re-targeting for SR1 Created attachment 200122 [details]
Loading models will happen outside of UI Thread.
Christopher, I took your patch and change it a bit, I took advantage of some already written code, that is used for the same purpose for J2EE models (ver. 1.4)
I also make it generic for all project types.
I have added some fixes for Application Client DD Node, since there were some triggers missing.
It won't still refresh correctly on first add, but I will address it in another bug.
@Chuck can you review the patch?
separate bug for App Client created: https://bugs.eclipse.org/bugs/show_bug.cgi?id=352841 looks ok - thanks Created attachment 201135 [details]
same patch just removed some not needed method that might cause NPE
reviewing the code before committing just noticed that the methods hasChildren can cause potential NPE
since some of them call getChildren().isEmpty() and getChildren can return null. Also noticed that there is already much safer hasChildren method in the parent class.
@Chuck I am not sure if I have to set it for review again? the difference into the patches is that the hasChildren method is deleted so the one in AbstractGroupProvider is user, which has safer implementation. With this patch I set javaee variable to null so it possible that NPE will appear without this fix. still looks good thanks targeting for SR2 Committed and release in HEAD and 3_3_Maintenance Dimitar, was this critical for WTP 3.4.0 M3 shutdown? I fixed the versioning problem that this caused (since those prevent us from declaring). We needed to rebuild because of the DTP prereq change... but a change like this probably should have waited until after the M3 declare. Sorry about that. I waited Friday releases to pass, but I have missed that M3 was not declared. |