package is.L42.connected.withSafeOperators.location; import java.util.ArrayList; import java.util.Collections; import java.util.List; import java.util.stream.Collectors; import ast.Ast; import ast.Ast.Path; import ast.ExpCore; import ast.ExpCore.ClassB; import ast.ExpCore.ClassB.NestedClass; import ast.PathAux; import facade.PData; import is.L42.connected.withSafeOperators.ExtractInfo; import is.L42.connected.withSafeOperators.ExtractInfo.ClassKind; import is.L42.connected.withSafeOperators.pluginWrapper.RefactorErrors.NotAvailable; public class Lib extends Location.LocationImpl<ExpCore.ClassB,Lib>{ boolean isBinded; ExpCore.ClassB root; Path path; public Lib( boolean isBinded, ExpCore.ClassB root, Path path, ExpCore.ClassB inner,Lib location) {super(inner,location); this.isBinded=isBinded; this.root=root; this.path=path; } public Lib( boolean isBinded, ExpCore.ClassB root, Path path, ExpCore.ClassB inner) {super(inner,null); this.isBinded=isBinded; this.root=root; this.path=path; this.location=this; } public static Lib newFromClass(PData pData,Path path){ ClassB cb=pData.p.extractClassB(path);//TODO: need from?? Lib lib=new Lib(true,cb,Path.outer(0),cb); return lib; } public static Lib newFromLibrary(ExpCore.ClassB cb){ Lib lib=new Lib(false,cb,Path.outer(0),cb); return lib; } Cacher<List<Lib>> nestedsC=new Cacher<List<Lib>>(){public List<Lib> cache(){ if(Lib.this.isBinded){ return inner.ns().stream() .map(n->new Lib(true,(ExpCore.ClassB)n.getInner(),Path.outer(0),(ExpCore.ClassB)n.getInner())) .collect(Collectors.toList()); } return inner.ns().stream() .map(n->new Lib(false,root,path.pushC(n.getName()),(ExpCore.ClassB)n.getInner(),Lib.this)) .collect(Collectors.toList()); }}; public int nestedsSize(){return nestedsC.get().size();} public Lib nested(int that) throws NotAvailable{return Location.listAccess(nestedsC.get(), that);} Cacher<List<Method>> methodsC=new Cacher<List<Method>>(){public List<Method> cache(){ return inner.mwts().stream() .map(mwt->new Method(mwt,Lib.this)) .collect(Collectors.toList());}}; public int methodsSize(){return methodsC.get().size();} public Method method(int that) throws NotAvailable{return Location.listAccess(methodsC.get(), that);} Cacher<List<Type.Implemented>> implementedsC=new Cacher<List<Type.Implemented>>(){public List<Type.Implemented> cache(){ List<Type.Implemented> res=new ArrayList<>(); {int i=-1; for(Ast.Type ti:inner.getSupertypes()){i+=1; //starts from 0 res.add(new Type.Implemented(i,ti.getNT(),inner,Lib.this)); }} return res; }}; public int implementedsSize(){return implementedsC.get().size();} public Type.Implemented implemented(int that) throws NotAvailable{return Location.listAccess(implementedsC.get(), that);} @Override public Doc doc(){return new Doc(inner.getDoc1(),this);} public String kindS(){ ClassKind k = ExtractInfo.classKind(root,path.getCBar(),inner,null,null,null); return k.name42; } public boolean isCoherent(PData pData){ return newTypeSystem.TsLibrary.coherent(pData.p.evilPush(this.inner), false); //TODO: no, we need to navigate on a path for classAnys? } public Lib root(){ if(this.root==this.inner){return this;} assert !this.isBinded; return new Lib(false,root,Path.outer(0),root); } public Path path(){return path;}//last is its name, empty path for root public Doc nestedDoc(){ if(this.path.getCBar().isEmpty()){ return new Doc(Ast.Doc.empty(),this); } NestedClass nc = inner.getNested(path.getCBar()); return new Doc(nc.getDoc(),this); }//empty doc if it is root //even if obtained with a classObj, no method to get it back //to get a nested classObj, Refactor.navigateClassObj(classAny,Path)->classAny?? public String toS() {return sugarVisitors.ToFormattedText.of(inner);} public Lib navigate(List<Ast.C> cs){ if (cs.isEmpty()){return this;} if(this.isBinded){ ClassB cb=this.inner.getClassB(cs);//TODO: need from? return new Lib(true,cb,Path.outer(0),cb); } List<Ast.C> top = Collections.singletonList(cs.get(0)); List<Ast.C> tail=cs.subList(1,cs.size()); Lib nextStep=new Lib(false,root,path.pushC(cs.get(0)),inner.getClassB(top),this); return nextStep.navigate(tail); } @Override public boolean equalequal(Object that) { return this.equals(that); } }