001package org.biopax.paxtools.impl.level3; 002 003import org.apache.commons.logging.Log; 004import org.apache.commons.logging.LogFactory; 005import org.biopax.paxtools.model.level3.BiochemicalPathwayStep; 006import org.biopax.paxtools.model.level3.Conversion; 007import org.biopax.paxtools.model.level3.Process; 008import org.biopax.paxtools.model.level3.StepDirection; 009import org.biopax.paxtools.util.IllegalBioPAXArgumentException; 010import org.hibernate.annotations.Cache; 011import org.hibernate.annotations.*; 012import org.hibernate.search.annotations.Indexed; 013 014import javax.persistence.Entity; 015import javax.persistence.*; 016import java.util.AbstractSet; 017import java.util.Iterator; 018import java.util.NoSuchElementException; 019import java.util.Set; 020 021@Entity @Proxy(proxyClass = BiochemicalPathwayStep.class) @Indexed @DynamicUpdate @DynamicInsert 022@Cache(usage = CacheConcurrencyStrategy.NONSTRICT_READ_WRITE) 023public class BiochemicalPathwayStepImpl extends PathwayStepImpl implements BiochemicalPathwayStep 024{ 025 private Conversion stepConversion; 026 027 private StepDirection stepDirection; 028 029 private Set<Process> stepProcess = new StepProcessSet(); 030 031 private Log log = LogFactory.getLog(BiochemicalPathwayStepImpl.class); 032 033 public BiochemicalPathwayStepImpl() 034 { 035 036 } 037 038 // 039 // utilityClass interface implementation 040 // 041 //////////////////////////////////////////////////////////////////////////// 042 @Transient 043 public Class<? extends BiochemicalPathwayStep> getModelInterface() 044 { 045 return BiochemicalPathwayStep.class; 046 } 047 048 // 049 // biochemicalPathwayStep interface implementation 050 // 051 //////////////////////////////////////////////////////////////////////////// 052 053 054 //trivial private setter/getter for ORM frameworks only 055 @ManyToOne(targetEntity = ConversionImpl.class) Conversion getStepConversionX() 056 { 057 return stepConversion; 058 } 059 060 void setStepConversionX(Conversion conversion) 061 { 062 this.stepConversion = conversion; 063 } 064 065 // Property stepConversion 066 @Transient 067 public Conversion getStepConversion() 068 { 069 return stepConversion; 070 } 071 072 /** 073 * {@inheritDoc} 074 */ 075 public void setStepConversion(Conversion highLander) 076 077 { 078 if (this.stepConversion != null) 079 { 080 if (this.stepConversion == highLander) 081 return; 082 else { 083 synchronized (this.stepConversion) { 084 this.stepConversion.getStepProcessOf().remove(this); 085 } 086 } 087 } 088 089 this.stepConversion = highLander; //can be null! 090 091 if(this.stepConversion != null) { 092 synchronized (this.stepConversion) { 093 this.stepConversion.getStepProcessOf().add(this); 094 } 095 } 096 097 } 098 099 @Override 100 public void addStepProcess(Process process) 101 { 102 if (process instanceof Conversion) 103 { 104 if (this.stepConversion == null || this.stepConversion == process) 105 { 106 log.debug("Ignoring request to add a Conversion as stepProcess"); 107 } else 108 { 109 throw new IllegalBioPAXArgumentException( 110 "Biochemical Pathway Step can have only one conversion. Did you want to use" + 111 "the setStepConversion method? "); 112 } 113 } 114 super.addStepProcess(process); 115 } 116 117 // Property STEP-DIRECTION 118 119 @Enumerated(EnumType.STRING) 120 public StepDirection getStepDirection() 121 { 122 return stepDirection; 123 } 124 125 public void setStepDirection(StepDirection newSTEP_DIRECTION) 126 { 127 stepDirection = newSTEP_DIRECTION; 128 } 129 130 @Transient @Override public Set<Process> getStepProcess() 131 { 132 return stepProcess; 133 } 134 135 136 private class StepProcessSet extends AbstractSet<Process> 137 { 138 @Override public Iterator<Process> iterator() 139 { 140 final Iterator<Process> proci = BiochemicalPathwayStepImpl.super.getStepProcess().iterator(); 141 142 return new Iterator<Process>() 143 { 144 boolean procEnd = false; 145 146 @Override public boolean hasNext() 147 { 148 return proci.hasNext() || !(procEnd || stepConversion == null); 149 } 150 151 @Override public Process next() 152 { 153 if (procEnd) throw new NoSuchElementException(); 154 if (proci.hasNext()) return proci.next(); 155 else 156 { 157 procEnd = true; 158 if (stepConversion == null) throw new NoSuchElementException(); 159 else return stepConversion; 160 } 161 } 162 163 @Override public void remove() 164 { 165 throw new UnsupportedOperationException(); 166 } 167 }; 168 } 169 170 @Override public int size() 171 { 172 return BiochemicalPathwayStepImpl.super.getStepProcess().size() + (stepConversion == null ? 0 : 1); 173 } 174 175 @Override public boolean contains(Object o) 176 { 177 return o != null && ((stepConversion != null && stepConversion.equals(o)) || BiochemicalPathwayStepImpl 178 .super.getStepProcess().contains(o)); 179 } 180 181 } 182}