I have a Navigation class where I am dynamically creating the navigation I am having two tables folder(it is directory that contains files) and content(it is like files or pages that will render the content on the public site). I have created a Navigation class in which I am having a wrapper class for merging the fields of content into the folder. I have tried using #OrderBy and #OrderColumn but I came to know that it will only work with collections.
List<Folder> folder = folderRepository.findAllByNavDepthLessThanOrderByNavDepthAsc(3);
here I am sorting it with navDepth(this column belongs to Folder entity) I also want to sort it with navOrder(this column belongs to Content entity)
#Service
public class NavigationService {
#Qualifier("jdbcMySQL")
private JdbcTemplate jdbcTemplate;
private FolderRepository folderRepository;
private FolderService folderService;
#Autowired
public NavigationService(JdbcTemplate jdbcTemplate,
FolderRepository folderRepository,
FolderService folderService) {
this.jdbcTemplate = jdbcTemplate;
this.folderRepository = folderRepository;
this.folderService = folderService;
}
#Transactional(propagation=Propagation.REQUIRED, readOnly=false)
public Map<String, NavigationItem> navigationItems() {
// TODO: // CROSS cutting AOP springs
// TODO: http://docs.spring.io/spring/docs/4.2.0.BUILD-SNAPSHOT/spring-framework-reference/htmlsingle/#aop
List<Folder> folder = folderRepository.findAllByNavDepthLessThanOrderByNavDepthAsc(3);
// List<Folder> folder = folderService.navigation();
Map<String, NavigationItem> navItems = new LinkedHashMap<String, NavigationService.NavigationItem>();
for (int i = 0; i < folder.size(); i++) {
NavigationItem ni = new NavigationItem();
ni.setNavDepth((int) (folder.get(i).getNavDepth()));
ni.setFileNamePath(folder.get(i).getDirectoryPath());
ni.setFilepath(folder.get(i).getDirectoryPath());
ni.setChildren(folder.get(i).getContent());
for (int k = 0; k < folder.size(); k++) {
if(folder.get(i).getId() == folder.get(k).getParentId()) {
ni.addSubFolder(folder.get(k));
System.out.println(folder.get(i).getTitle());
System.out.println(folder.get(k));
System.out.println("---!!!!!!________----------!!!!!!!!");
}
}
navItems.put(folder.get(i).getTitle(), ni);
}
return navItems;
}
public class NavigationItem {
private long id;
private long parentId;
private String title;
private String fileName;
private String fileNamePath;
private int navDepth;
private int navOrder;
private String parentFileName;
private String filePath;
private String folderName;
#OrderColumn(name="navOrder ASC")
private List<Content> children = new ArrayList();
private ArrayList<Folder> subFolder = new ArrayList();
public void setSubFolder(ArrayList<Folder> subFolder) {
this.subFolder = subFolder;
}
public String getFilePath() {
return filePath;
}
public void setFilePath(String filePath) {
this.filePath = filePath;
}
public String getFolderName() {
return folderName;
}
public void setFolderName(String folderName) {
this.folderName = folderName;
}
public ArrayList<Folder> getSubFolder() {
return subFolder;
}
public void addSubFolder(Folder subFolder) {
this.subFolder.add(subFolder);
}
public void setChildren(List<Content> list) {
this.children = list;
}
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public long getParentId() {
return parentId;
}
public void setParentId(long parentId) {
this.parentId = parentId;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getFileName() {
return fileName;
}
public void setFileName(String fileName) {
this.fileName = fileName;
}
public String getFileNamePath() {
return fileNamePath;
}
public void setFileNamePath(String fileNamePath) {
this.fileNamePath = fileNamePath;
}
public long getNavDepth() {
return navDepth;
}
public void setNavDepth(int navDepth) {
this.navDepth = navDepth;
}
public long getNavOrder() {
return navOrder;
}
public void setNavOrder(int navOrder) {
this.navOrder = navOrder;
}
public String getParentFileName() {
return parentFileName;
}
public void setParentFileName(String parentFileName) {
this.parentFileName = parentFileName;
}
public List<Content> getChildren() {
return children;
}
public void addChild(Content child) {
children.add(child);
}
public String getFilepath() {
return filePath;
}
public void setFilepath(String filePath) {
this.filePath = filePath;
}
}
}
Use a Comparator<NavigationItem> and pass that to Collections.sort() or similar methods.
The comparator might look like this:
class NavComparator implements Comparator<NavigationItem> {
int specialValueNoChildren = -1; //assuming nav_order is always 0 or greater
int compare(NavigationItem o1, NavigationItem o2) {
int max1 = getMaxNavOrder( o1 );
int max2 = getMaxNavOrder( o2 );
return Integer.compare( max1, max2 );
}
int getMaxNavOrder( NavigationItem ni ) {
int max = specialValueNoChildren;
for( Content child : ni.getChildren() ) {
max = Math.max(max, child.getNavOrder());
}
return max;
}
}
Here the maximum nav order of all children is selected with -1 being the special case of no children. Then the items are compared by their respective children's maximum nav order.
If you need a different order change that accordingly, e.g. by reversing max1 and max2 or by getting the lowest nav order of the children etc.
Related
I am doing a liferay project which use ejb at back end. so my ejb method looks like this:-
#Override
public List<RmisPaymentDetailsDto> getEpaymentDetails(String ebpCode) {
Query q = entityManager.createQuery("select s from EpaymentBo s where s.ebpCode=:ebpcode")
.setParameter("ebpcode",ebpCode);
#SuppressWarnings("unchecked")
List<ProductBo> list = q.getResultList();
Iterator<ProductBo> i = list.iterator();
List<RmisPaymentDetailsDto> rList = new ArrayList<RmisPaymentDetailsDto>();
while(i.hasNext()){
EpaymentBo ep =(EpaymentBo) i.next();
RmisPaymentDetailsDto dto = new RmisPaymentDetailsDto();
dto.setAdvertisementcode(ep.getAdvertisementcode());
dto.setAmount(ep.getAmount());
dto.setStudentmasterid(ep.getStudentmasterid());
dto.setEbpgendate(ep.getEbp_gen_date());
dto.setEbpcode(ep.getEbpCode());
dto.setPaymentstatus(ep.getPaymentstatus());
dto.setCandidatenameinnepali(ep.getCandidatenameinnepali());
rList.add(dto);
}
return rList;
}
the above method successfully fetches data from database and sets it to my RmisPaymentDetailsDto.
like this:-
now i am calling same method from my liferay controlller.
PreExaminationRemote preRef = (PreExaminationRemote) jndiContext
.lookup("PreExamination/remote");
List<RmisPaymentDetailsDto> rDto = preRef.getEpaymentDetails(ebpCode);
I am wondering how my one property(candidatenameinnepali) is lost as i return same dto from my ejb.
My dto looks like this:-
public class RmisPaymentDetailsDto implements Serializable {
private static final long serialVersionUID = 1L;
private String advertisementcode;
private String ebpcode;
private String amount;
private String studentmasterid;
private Date ebpgendate;
private String paymentstatus;
private String candidatenameinnepali;
public String getCandidatenameinnepali() {
return candidatenameinnepali;
}
public void setCandidatenameinnepali(String candidatenameinnepali) {
this.candidatenameinnepali = candidatenameinnepali;
}
public String getAdvertisementcode() {
return advertisementcode;
}
public void setAdvertisementcode(String advertisementcode) {
this.advertisementcode = advertisementcode;
}
public String getEbpcode() {
return ebpcode;
}
public void setEbpcode(String ebpcode) {
this.ebpcode = ebpcode;
}
public String getAmount() {
return amount;
}
public void setAmount(String amount) {
this.amount = amount;
}
public String getStudentmasterid() {
return studentmasterid;
}
public void setStudentmasterid(String studentmasterid) {
this.studentmasterid = studentmasterid;
}
public Date getEbpgendate() {
return ebpgendate;
}
public void setEbpgendate(Date ebpgendate) {
this.ebpgendate = ebpgendate;
}
public String getPaymentstatus() {
return paymentstatus;
}
public void setPaymentstatus(String paymentstatus) {
this.paymentstatus = paymentstatus;
}
public static long getSerialversionuid() {
return serialVersionUID;
}
}
I am currently working on a project using the Spring framework and SpringData MongoDB (v.1.6.1 RELEASE). I now want to add a property to a stored object, that would simplify its retrieval, but I need to compute this property based on the state of the object at the point of time I want to save it. I tried to put that computation within the getter method of the object, but somehow SpringData is not using the getter to access the property.
The concrete example is the following:
I am storing events in the database and the events are allowed to span over several dates, creating a multi-date event. The events are defined by a start date (LocalDateTime) and an end date (LocalDateTime). I now want to store the information, if the event is a multi-date event or not, within the database. Concluding I added a boolean variable to the event (multiDate). Within the getter (isMultiDate) I am comparing the start and end date and returning true or false (depending on the dates).
My event object:
public class Event
{
#Id
private String id;
#NotBlank
private String name;
private String description;
private String location;
private double locationLat;
private double locationLog;
#NotNull
#JsonIgnore
private int startDateDayOfMonth, startDateMonth, startDateYear, startDateHour, startDateMinute;
#NotNull
#JsonIgnore
private int endDateDayOfMonth, endDateMonth,endDateYear, endDateHour, endDateMinute;
#LastModifiedDate
private Date lastChanged;
#Transient
private LocalDateTime startDateTime;
#Transient
private LocalDateTime endDateTime;
private boolean multiDate;
#DBRef
#NotEmpty
private List<Division> invitedDivision;
public Event() {}
public String getId()
{
return id;
}
public void setId(String id)
{
this.id = id;
}
public String getName()
{
return name;
}
public void setName(String name)
{
this.name = name;
}
public String getDescription()
{
return description;
}
public void setDescription(String description)
{
this.description = description;
}
public String getLocation()
{
return location;
}
public void setLocation(String location)
{
this.location = location;
}
public double getLocationLat()
{
return locationLat;
}
public void setLocationLat(double locationLat)
{
this.locationLat = locationLat;
}
public double getLocationLog()
{
return locationLog;
}
public void setLocationLog(double locationLog)
{
this.locationLog = locationLog;
}
public int getStartDateDayOfMonth()
{
return startDateDayOfMonth;
}
public void setStartDateDayOfMonth(int startDateDayOfMonth)
{
this.startDateDayOfMonth = startDateDayOfMonth;
}
public int getStartDateMonth()
{
return startDateMonth;
}
public void setStartDateMonth(int startDateMonth)
{
this.startDateMonth = startDateMonth;
}
public int getStartDateYear()
{
return startDateYear;
}
public void setStartDateYear(int startDateYear)
{
this.startDateYear = startDateYear;
}
public int getStartDateHour()
{
return startDateHour;
}
public void setStartDateHour(int startDateHour)
{
this.startDateHour = startDateHour;
}
public int getStartDateMinute()
{
return startDateMinute;
}
public void setStartDateMinute(int startDateMinute)
{
this.startDateMinute = startDateMinute;
}
public int getEndDateDayOfMonth()
{
return endDateDayOfMonth;
}
public void setEndDateDayOfMonth(int endDateDayOfMonth)
{
this.endDateDayOfMonth = endDateDayOfMonth;
}
public int getEndDateMonth()
{
return endDateMonth;
}
public void setEndDateMonth(int endDateMonth)
{
this.endDateMonth = endDateMonth;
}
public int getEndDateYear()
{
return endDateYear;
}
public void setEndDateYear(int endDateYear)
{
this.endDateYear = endDateYear;
}
public int getEndDateHour()
{
return endDateHour;
}
public void setEndDateHour(int endDateHour)
{
this.endDateHour = endDateHour;
}
public int getEndDateMinute()
{
return endDateMinute;
}
public void setEndDateMinute(int endDateMinute)
{
this.endDateMinute = endDateMinute;
}
public Date getLastChanged()
{
return lastChanged;
}
public void setLastChanged(Date lastChanged)
{
this.lastChanged = lastChanged;
}
public LocalDateTime getStartDateTime()
{
startDateTime = LocalDateTime.of(startDateYear, startDateMonth, startDateDayOfMonth, startDateHour, startDateMinute);
return startDateTime;
}
public void setStartDateTime(LocalDateTime startDateTime)
{
this.startDateTime = startDateTime;
if(startDateTime != null)
{
startDateYear = startDateTime.getYear();
startDateMonth = startDateTime.getMonthValue();
startDateDayOfMonth = startDateTime.getDayOfMonth();
startDateHour = startDateTime.getHour();
startDateMinute = startDateTime.getMinute();
}
}
public LocalDateTime getEndDateTime()
{
endDateTime = LocalDateTime.of(endDateYear, endDateMonth, endDateDayOfMonth, endDateHour, endDateMinute);
return endDateTime;
}
public void setEndDateTime(LocalDateTime endDateTime)
{
this.endDateTime = endDateTime;
if(endDateTime != null)
{
endDateYear = endDateTime.getYear();
endDateMonth = endDateTime.getMonthValue();
endDateDayOfMonth = endDateTime.getDayOfMonth();
endDateHour = endDateTime.getHour();
endDateMinute = endDateTime.getMinute();
}
}
public List<Division> getInvitedDivision()
{
return invitedDivision;
}
/**
* The function is setting all invited divisions, but is optimizing the set by eliminating unnecessary divisions.
* #param invitedDivision
*/
public void setInvitedDivision(List<Division> invitedDivision)
{
if(invitedDivision != null)
{
this.invitedDivision = DivisionManagementController.getOptimizedSetOfDivisions(invitedDivision);
} else
{
this.invitedDivision = invitedDivision;
}
}
public void addDivision(Division division)
{
if(invitedDivision == null)
{
invitedDivision = new ArrayList<>();
}
invitedDivision.add(division);
}
public boolean isMultiDate()
{
return (startDateDayOfMonth != endDateDayOfMonth) || (startDateMonth != endDateMonth) || (startDateYear != endDateYear);
}
public void setMultiDate(boolean multiDate)
{
this.multiDate = multiDate;
}
}
What am I getting wrong? Why is SpringData not using the public getter to access a private variable? (I actually returned always true and the database still only showed storing false).
Thanks in advance!
I am still not clear about the issue, but try this
public boolean isMultiDate()
{
multiDate = (startDateDayOfMonth != endDateDayOfMonth) || (startDateMonth != endDateMonth) || (startDateYear != endDateYear);
return multiDate;
}
I have an arrayList with following values:
static ArrayList<DTONodeDetail> tree;
public static void main(String[] args) {
// TODO Auto-generated method stub
tree=new ArrayList<DTONodeDetail>();
//first argument->NodeId
//second->NodeName
// third -> ParentNodeId
tree.add(getDTO(1,"Root",0));
tree.add(getDTO(239,"Node-1",1));
tree.add(getDTO(242,"Node-2",239));
tree.add(getDTO(243,"Node-3",239));
tree.add(getDTO(244,"Node-4",242));
tree.add(getDTO(245,"Node-5",243));
displayTree(tree.get(0));
}
public static DTONodeDetail getDTO(int nodeId,String nodeName,int parentID)
{
DTONodeDetail dto=new DTONodeDetail();
dto.setNodeId(nodeId);
dto.setNodeDisplayName(nodeName);
dto.setParentID(parentID);
return dto;
}
Now i want to display above data in tree structure as below using simple java code:
Root
-----Node-1
------------Node-2
------------------Node-4
------------Node-3
------------------Node-5
I have tried following but unable to get desire result:
public static void displayTree(DTONodeDetail dto){
ArrayList<DTONodeDetail> childs = selectChild(dto.getNodeId());
System.out.println(dto.getNodeDisplayName());
for(DTONodeDetail obj:childs){
displayTree(obj);
}
}
public static ArrayList<DTOWorkSpaceNodeDetail> selectChild(int nodeID){
ArrayList<DTOWorkSpaceNodeDetail> list=new ArrayList<DTOWorkSpaceNodeDetail>();
for(int i=0;i<tree.size();i++)
{
if(tree.get(i).getParentID()==nodeID){
list.add(tree.get(i));
}
}
return list;
}
Please Provide some guide or code.
You should do like this
static void displayTree(DTONodeDetail root ,int level){
System.out.print(prefix(level));
System.out.println(root.name);
ArrayList<DTONodeDetail> children = selectChild(dto.getNodeId());
for(DTONodeDetail child : children){
displayTree(child, level + 1);
}
}
the prefix is a func to build enough '----'
static String prefix(int level){
StringBuilder s = new StringBuilder();
for(int i = 0; i < level; i++){
s.append("----");
}
return s.toString();
}
Result
displayTree(node1, 0);
Node-1
----Node-2
--------Node-4
----Node-3
--------Node-5
The only problem with your implementation that I see, is that the output is as expected, but flat (i.e. no ---- at the beginning of child lines). This is because displayTree() currently has no way of knowing at which level the node it is printing is.
I propose this:
public static void displayTree(DTONodeDetail dto, int charsBeforeNodename){
ArrayList<DTONodeDetail> childs = selectChild(dto.getNodeId());
for(int i = 0; i <= charsBeforeNodename; i++){
System.out.println("-");
}
System.out.println(dto.getNodeDisplayName());
for(DTONodeDetail obj:childs){
displayTree(obj, charsBeforeNodename + dto.getNodeDisplayName().length());
}
}
Sorry, I misunderstood the question.
I updated them.
public class DTONodeDetail {
private int nodeId;
private String nodeName;
private int parentId;
public DTONodeDetail() {
}
public DTONodeDetail(int nodeId, String nodeName, int parentId) {
this.nodeId = nodeId;
this.nodeName = nodeName;
this.parentId = parentId;
}
public int getNodeId() {
return nodeId;
}
public void setNodeId(int nodeId) {
this.nodeId = nodeId;
}
public String getNodeName() {
return nodeName;
}
public void setNodeName(String nodeName) {
this.nodeName = nodeName;
}
public int getParentId() {
return parentId;
}
public void setParentId(int parentId) {
this.parentId = parentId;
}
private static List<DTONodeDetail> tree;
public static DTONodeDetail getDTO(int nodeId, String nodeName, int parentID) {
DTONodeDetail dto = new DTONodeDetail();
dto.setNodeId(nodeId);
dto.setNodeName(nodeName);
dto.setParentId(parentID);
return dto;
}
private static List<DTONodeDetail> selectChildren(int parentId) {
List<DTONodeDetail> result = new ArrayList<DTONodeDetail>();
for (DTONodeDetail d : tree) {
if (d.getParentId() == parentId) {
result.add(d);
}
}
return result;
}
public static void displayTree(DTONodeDetail dto, int level) {
List<DTONodeDetail> childs = selectChildren(dto.getNodeId());
String space = "";
for (int i = 0; i < level; i++) {
space += "\t";
}
System.out.println(space + dto.getNodeName());
if(childs.size()>0){
level ++;
}
for (DTONodeDetail obj : childs) {
displayTree(obj, level);
}
}
public static void main(String[] args) {
tree = new ArrayList<DTONodeDetail>();
tree.add(getDTO(1, "Root", 0));
tree.add(getDTO(239, "Node_1", 1));
tree.add(getDTO(242, "Node_2", 239));
tree.add(getDTO(243, "Node_3", 239));
tree.add(getDTO(244, "Node_4", 242));
tree.add(getDTO(245, "Node_5", 243));
displayTree(tree.get(0), 0);
}
}
Result:
Root
Node_1
Node_2
Node_4
Node_3
Node_5
i have a Java Enum like below
public enum TestEnum{
{
A("a","b","c"),
B("a1","b1","c1"),
C("a2","b2","c2");
TestEnum(String a,String b,String c){
}
private String a;
private String b;
private String c;
}
I want to externalize this config to an XML file but XSDs donot seem to support attributes on Enum Element type. Is there a way to work this around or an alternate to it.
You could do something like this (even though for enum, this looks too verbose)
#XmlJavaTypeAdapter(CountXmlAdapter.class)
public enum Count {
ONE(1, "one"),
TWO(2, "two"),
THREE(3, "three");
private final int index;
private final String name;
private Count(int index, String name) {
this.index = index;
this.name = name;
}
#XmlAccessorType(XmlAccessType.FIELD)
public static class CountWrapper {
private int index;
private String name;
public CountWrapper() {
}
public CountWrapper(int index, String name) {
this.index = index;
this.name = name;
}
}
public static class CountXmlAdapter extends XmlAdapter<CountWrapper, Count> {
#Override
public Count unmarshal(CountWrapper v) throws Exception {
return v != null ? Count.valueOf(v.name.toUpperCase()) : null;
}
#Override
public CountWrapper marshal(Count v) throws Exception {
return v != null ? new CountWrapper(v.index, v.name) : null;
}
}
}
I am working in an android application I want to sort a List of Objects with an Object Property. I have sorted it successfully but when I sort it all the List with that object changes the value to same as the sorted value
Please look into ma code :
SortedSet<Caseload> removeDuplicateClientName = new TreeSet<Caseload>(
new Comparator<Caseload>() {
#Override
public int compare(Caseload caseload0, Caseload caseload1) {
return caseload0.ClientName.compareTo(caseload1.ClientName);
}
});
// Getting the list of values from web service
mLISTCaseloadsHeads = parsedXML.getCaseLoadValues("get_Caseload_ClientServiceGroupID", param);
List<Caseload> newBackUp=mLISTCaseloadsHeads ;
Iterator<Caseload> iterator = mCaseloadsHeads.iterator();
while (iterator.hasNext()) {
removeDuplicateClientName.add(iterator.next());
}
mCaseloadsHeads.clear();
mCaseloadsHeads.addAll(removeDuplicateClientName);
The List newBackUp also changes the value to the same as sorted List
Caseload class:
public class Caseload implements Comparable<Caseload> {
public int BusClientLogID;
public int ClientID;
public int ClientStatus;
public int ClientServiceGroup_ClientSiteTherapyID;
public String ClientName;
public String TimeArrive;
public String TimeDepart;
public String SignOutTime;
public String SignInTime;
public String ServiceCompletedCount;
public Boolean ShowFooter = false;
public int getBusClientLogID() {
return BusClientLogID;
}
public void setBusClientLogID(int busClientLogID) {
BusClientLogID = busClientLogID;
}
public int getClientID() {
return ClientID;
}
public void setClientID(int clientID) {
ClientID = clientID;
}
public int getClientStatus() {
return ClientStatus;
}
public void setClientStatus(int clientStatus) {
ClientStatus = clientStatus;
}
public int getClientServiceGroup_ClientSiteTherapyID() {
return ClientServiceGroup_ClientSiteTherapyID;
}
public void setClientServiceGroup_ClientSiteTherapyID(
int clientServiceGroup_ClientSiteTherapyID) {
ClientServiceGroup_ClientSiteTherapyID = clientServiceGroup_ClientSiteTherapyID;
}
public String getClientName() {
return ClientName;
}
public void setClientName(String clientName) {
ClientName = clientName;
}
public String getTimeArrive() {
return TimeArrive;
}
public void setTimeArrive(String timeArrive) {
TimeArrive = timeArrive;
}
public String getTimeDepart() {
return TimeDepart;
}
public void setTimeDepart(String timeDepart) {
TimeDepart = timeDepart;
}
public String getSignOutTime() {
return SignOutTime;
}
public void setSignOutTime(String signOutTime) {
SignOutTime = signOutTime;
}
public String getSignInTime() {
return SignInTime;
}
public void setSignInTime(String signInTime) {
SignInTime = signInTime;
}
public String getServiceCompletedCount() {
return ServiceCompletedCount;
}
public void setServiceCompletedCount(String serviceCompletedCount) {
ServiceCompletedCount = serviceCompletedCount;
}
#Override
public int compareTo(Caseload compareCaseload) {
int busClientLogID = ((Caseload) compareCaseload).getBusClientLogID();
return busClientLogID - this.BusClientLogID;
}
}
Please give me a solution.
I doubt the return statement associated with your compare function in the comparator.
You should go by this approach to get the right ordering :
#Override
public int compare(YourClass lhs, YourClass rhs) {
YourClass p1 = (YourClass) lhs;
YourClass p2 = (YourClass) rhs;
int first = p1.ClientName; //use your getter if you want
int second = p2.ClientName;
if (second < first) {
return 1;
}
else if (second > first) {
return -1;
}
else {
return 0;
}
}
If you go by this approach I guess you will get the required ordering after sort.
Edit:
Now I have got the issue, you are using a reference of the original list in newBackup and its not a new list that is why this is happening, use this and you are good to go.
List<Caseload> newBackUp=new ArrayList<Caseload>(mLISTCaseloadsHeads);