/[projects]/android/TrainInfoServiceGoogle/src/dk/thoerup/traininfoservice/StationDAO.java
ViewVC logotype

Diff of /android/TrainInfoServiceGoogle/src/dk/thoerup/traininfoservice/StationDAO.java

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

android/TrainInfoService/src/dk/thoerup/traininfoservice/StationDAO.java revision 737 by torben, Wed May 19 07:40:00 2010 UTC android/TrainInfoServiceGoogle/src/dk/thoerup/traininfoservice/StationDAO.java revision 1113 by torben, Thu Sep 23 12:56:11 2010 UTC
# Line 1  Line 1 
1  package dk.thoerup.traininfoservice;  package dk.thoerup.traininfoservice;
2    
3  import java.sql.Connection;  import java.io.IOException;
 import java.sql.PreparedStatement;  
 import java.sql.ResultSet;  
 import java.sql.SQLException;  
 import java.sql.Statement;  
4  import java.util.ArrayList;  import java.util.ArrayList;
5    import java.util.Collections;
6    import java.util.Comparator;
7    import java.util.HashMap;
8  import java.util.List;  import java.util.List;
9    import java.util.Map;
10    import java.util.logging.Level;
11    import java.util.logging.Logger;
12    
13    import javax.jdo.Extent;
14    import javax.jdo.PersistenceManager;
15    import javax.jdo.Query;
16    
17    import net.sf.jsr107cache.Cache;
18    import net.sf.jsr107cache.CacheException;
19    import net.sf.jsr107cache.CacheManager;
20    
21    import com.google.appengine.api.memcache.jsr107cache.GCacheFactory;
22    
23    import dk.thoerup.android.traininfo.common.StationBean;
24    import dk.thoerup.android.traininfo.common.StationBean.StationEntry;
25    import dk.thoerup.traininfoservice.geo.Geo;
26    import dk.thoerup.traininfoservice.jdo.JdoStationBean;
27    import dk.thoerup.traininfoservice.jdo.PMF;
28    
29  public class StationDAO {  public class StationDAO {
30          private StationBean convertSingleRow(ResultSet res) throws SQLException {          final static int LOCATION_LIMIT = 8;
31                  StationBean station = new StationBean();          static final Logger logger = Logger.getLogger(StationDAO.class.getName());
32            
33            final int TIMEOUT_SECONDS = 30*60;
34            
35            Cache cache;
36            
37            public StationDAO() {
38            Map props = new HashMap();
39            props.put(GCacheFactory.EXPIRATION_DELTA, TIMEOUT_SECONDS);        
40                                    
41                  station.setId( res.getInt(1) );                  try {
42                  station.setName( res.getString(2) );              cache = CacheManager.getInstance().getCacheFactory().createCache(props);            
43                  station.setLatitude( res.getDouble(3) );          } catch (CacheException e) {
44                  station.setLongitude( res.getDouble(4) );                  logger.log(Level.WARNING, "error creating cache", e);
45                  station.setRegional( res.getString(5) );          }
46                  station.setStrain( res.getString(6) );          
47                  station.setMetro( res.getString(7) );          }
48                  station.setAddress( res.getString(8) );  
49                  station.setCalcdist( (int)res.getDouble(9) );  
50            public StationEntry getById(int id)  {
51    
52                    PersistenceManager pm = null;
53                                    
54                  return station;                  try {
55                            pm = PMF.get().getPersistenceManager();
56                            JdoStationBean bean =pm.getObjectById(JdoStationBean.class, new Integer(id) );
57                            return bean.toStationEntry();
58                    } finally {
59                            pm.close();
60                    }
61            }
62    
63            /* damn that JDO sucks so we to the filtering in java-code */
64            public StationBean getByName(String searchname) {
65                    PersistenceManager pm = null;
66                    
67                    try {
68                            /*pm = PMF.get().getPersistenceManager();
69                            
70                            
71                            
72                            Query q = pm.newQuery(JdoStationBean.class);
73                            q.setOrdering("name");                  
74                            List<JdoStationBean> beanList = (List<JdoStationBean>) q.execute();*/
75                            
76                            List<JdoStationBean> beanList = getAllStations();
77                            
78                            
79                            StationBean stationBean = new StationBean();
80                            
81                            searchname = searchname.toLowerCase();
82                            for(JdoStationBean bean : beanList) {
83                                    if (bean.getName().toLowerCase().startsWith(searchname)) {
84                                            stationBean.entries.add( bean.toStationEntry() );
85                                    } else {
86                                            for (String alias : bean.aliases ) {
87                                                    if (alias.toLowerCase().startsWith(searchname)) {
88                                                            stationBean.entries.add( bean.toStationEntry() );
89                                                    }
90                                            }
91                                    }
92                            }
93    
94                            return stationBean;                    
95                    } finally {
96                    //      pm.close();
97                    }
98          }          }
99                    
100          private List<StationBean> convertResultset(ResultSet res) throws SQLException {          public List<JdoStationBean> getAllStations() {
101                  List<StationBean> stations = new ArrayList<StationBean>();                  final String key = "allstations";
102                  while (res.next()) {                  List<JdoStationBean> result = (List<JdoStationBean>) cache.get(key);
103                          stations.add( convertSingleRow(res) );                  
104                    if (result == null) {
105                            logger.info("getAllStations Cache miss");
106                            
107                            PersistenceManager pm = null;
108                            final double LAT = 0.4;
109                            final double LNG = 0.75;
110                            
111                            try {
112                                    pm = PMF.get().getPersistenceManager();
113                                    Extent<JdoStationBean> all = pm.getExtent(JdoStationBean.class, false);
114                                    
115                                    result = new ArrayList<JdoStationBean>();
116                                    for (JdoStationBean station : all) {
117                                            result.add(station);
118                                    }
119                                    
120                                    cache.put(key, result);
121                                    
122                            } finally {
123                                    pm.close();
124                            }
125                    } else {
126                            logger.info("getAllStations Cache hit");
127                  }                  }
128                  return stations;                  
129                    
130                    
131                    return result;
132                                    
133          }          }
134                    
135    
136            //String limitExpression = (geolimit == true) ? "AND abs(latitude-?)<0.4 AND abs(longitude-?)<0.75 " : "";
137            /*
138            public List<JdoStationBean> getByLocationList(double latitude, double longitude, boolean geolimit)  {
139                    
140          public StationBean getById(int id) throws SQLException {                  PersistenceManager pm = null;
141                  String SQL = "SELECT id,name,latitude,longitude,stationcode_fjrn,stationcode_stog,stationcode_metro,address,0.0 " +                  final double LAT = 0.4;
142                        "FROM trainstations WHERE id=" + id + " AND enabled=true";                  final double LNG = 0.75;
                   
                 Connection conn = null;  
                 Statement stmt = null;  
                 ResultSet res = null;  
                 StationBean result;  
143                                    
144                  try {                  try {
145                          conn = DBConnection.getConnection();                          pm = PMF.get().getPersistenceManager();
146                                            Query q = pm.newQuery(JdoStationBean.class);
147                          stmt = conn.createStatement();                          
148                          res = stmt.executeQuery(SQL);                                    
149                          res.next();                          
150                          result = convertSingleRow(res);                          if (geolimit == true) {
151                                    double minLat = latitude - LAT;
152                                    double maxLat = latitude + LAT;
153                                    
154                                    //DAMN JDO implementation only allows us to compare on one parameter
155    
156                                    String filter = String.format("latitude > %f && latitude < %f", minLat, maxLat);
157                                    
158                                    q.setFilter( filter );
159                            }
160                            
161                            List<JdoStationBean> beanList = (List<JdoStationBean>) q.execute();                    
162                            
163                            logger.info("beanList size " + beanList.size());
164                            
165                            return beanList;
166                  } finally {                  } finally {
167                          if (res != null)                          pm.close();
                                 res.close();  
                         if (stmt != null)  
                                 stmt.close();  
                         if (conn != null)  
                                 conn.close();  
168                  }                  }
169            }*/
170    
171    
172            public StationBean getByLocation(double latitude, double longitude)  {
173                    /*
174                    List<JdoStationBean> beanList = getByLocationList(latitude,longitude,true);
175                                    
176                  return result;                  if (beanList.size() < LOCATION_LIMIT ) {
177                            logger.info("getByLocation failover: " +latitude + "," + longitude);
178                            beanList = getByLocationList(latitude,longitude, false);
179                    }*/
180                    
181                    List<JdoStationBean> beanList = getAllStations();
182    
183                    StationBean stationBean = new StationBean();                    
184    
185    
186                    Geo location = new Geo(latitude,longitude);
187                    for(JdoStationBean bean : beanList) {
188                            double meter = Geo.distanceKM( location, new Geo(bean.getLatitude(), bean.getLongitude() )) * 1000.0;
189    
190                            bean.distance = (int) meter;
191                    }
192    
193    
194                    Collections.sort(beanList, new Comparator<JdoStationBean>() {
195                            @Override
196                            public int compare(JdoStationBean o1, JdoStationBean o2) {
197                                    if (o1.distance < o2.distance) {
198                                            return -1;
199                                    } else if (o1.distance > o2.distance) {
200                                            return 1;
201                                    } else {
202                                            return 0;
203                                    }
204                            }
205                    });
206    
207                    for (int i=0; i<LOCATION_LIMIT && i<beanList.size(); i++) {
208                            stationBean.entries.add( beanList.get(i).toStationEntry() );
209                    }
210    
211                    return stationBean;                    
212          }          }
213                    
214          /*  
215           * this code requires theses statements are run on database in order to do ILIKE searches against aliases (which is defines as array of varchar(64) )          public StationBean getByList(String list)  {
216           *     create function rlike(text,text) returns bool as                  PersistenceManager pm = null;
217           *     'select $2 ilike $1' language sql strict immutable;                  
218       *     create operator ~~~ (procedure = rlike, leftarg = text, rightarg = text, commutator = ~~);                  try {
219           */                          String parts[] = list.split(",");
220          public List<StationBean> getByName(String name) throws SQLException {                          
221                  String SQL = "SELECT id,name,latitude,longitude,stationcode_fjrn,stationcode_stog, stationcode_metro, address, 0.0 " +                          StringBuilder filter = new StringBuilder();
222                  "FROM trainstations " +                          
223                  "WHERE (name ILIKE ? OR ? ~~~ ANY(aliases)) AND enabled = true " +                          for(String part : parts)  {
224                  "ORDER BY name ";                                  if (filter.length() > 0) {
225                                            filter.append( " || " );
226                                                    }
227                  List<StationBean> result;                                  filter.append("id == ").append(part);
228                  Connection conn = null;                          }                      
229                  PreparedStatement stmt = null;                          
230                  ResultSet res = null;                          //String filter = "id == 10 || id == 82"; //TODO: build filter
231                  try {                          
232                          conn = DBConnection.getConnection();                          pm = PMF.get().getPersistenceManager();
233                          stmt = conn.prepareStatement(SQL);                          Query q = pm.newQuery(JdoStationBean.class);
234                                                    q.setFilter( filter.toString() );
235                          stmt.setString(1, name + "%");                          q.setOrdering("name");
236                          stmt.setString(2, name + "%");                          
237                                                    List<JdoStationBean> beanList = (List<JdoStationBean>) q.execute();
238                          res = stmt.executeQuery();                          
239                          result = convertResultset(res);                          StationBean stationBean = new StationBean();
240                                                    
241                  } finally {                          for(JdoStationBean bean : beanList) {
242                          if (res != null)                                  stationBean.entries.add( bean.toStationEntry() );
243                                  res.close();                          }
244                          if (stmt != null)  
245                                  stmt.close();                          return stationBean;                    
246                          if (conn!= null)                  } finally {
247                                  conn.close();                          pm.close();
248                  }                  }
249                  return result;  
250          }          }
251            
252          //the "hack" with max 2.5 degrees latitude and longitude is only valid since we only service danish trains  
253          public List<StationBean> getByLocation(double latitude, double longitude) throws SQLException {          public int getIdByName(String name)  {
254                  String SQL = "SELECT id,name,latitude,longitude,stationcode_fjrn,stationcode_stog, stationcode_metro, address," +                  
255                                           "       earth_distance( earth_coord, ll_to_earth(?,?))::int AS calcdist " +                  List<JdoStationBean> beanList = null;
256                                           "FROM trainstations " +                  
257                                           "WHERE enabled = true AND abs(latitude-?)<2.5 AND abs (longitude-?)<2.5 " +                  PersistenceManager pm = null;
258                                           "ORDER BY calcdist ASC " +                  
259                                           "LIMIT 4 ";                  try {
260                  List<StationBean> result;                          
261                  Connection conn = null;                          String filter = " name == '" + name + "'";
262                  PreparedStatement stmt = null;                          
263                  ResultSet res = null;                          pm = PMF.get().getPersistenceManager();
264                  try {                          Query q = pm.newQuery(JdoStationBean.class);
265                          conn = DBConnection.getConnection();                          q.setFilter(filter);
266                          stmt = conn.prepareStatement(SQL);                          
267                          stmt.setDouble(1, latitude);                          beanList = (List<JdoStationBean>) q.execute();
268                          stmt.setDouble(2, longitude);                          
269                          stmt.setDouble(3, latitude);                          StationBean stationBean = new StationBean();
270                          stmt.setDouble(4, longitude);                                            
271                          res = stmt.executeQuery();                          for(JdoStationBean bean : beanList) {
272                          result = convertResultset(res);                                  stationBean.entries.add( bean.toStationEntry() );
273                                                    }
274                  } finally {                          
275                          if (res != null)                  } finally {
276                                  res.close();                          pm.close();
277                          if (stmt != null)                  }
278                                  stmt.close();  
279                          if (conn!= null)                  if ( beanList != null && beanList.size()  == 1) {
280                                  conn.close();                          return (int) beanList.get(0).getId();
281                    } else {
282                            return -1;
283                  }                  }
                 return result;  
284          }          }
285                    
286           public List<StationBean> getByList(String list) throws SQLException {          @SuppressWarnings("unchecked")
287                          String SQL = "SELECT id,name,latitude,longitude,stationcode_fjrn,stationcode_stog,stationcode_metro, address,0.0 " +          public int saveStations(StationBean stationBean) throws IOException {
288                          "FROM trainstations " +                  PersistenceManager pm = null;
289                          "WHERE id IN " + list + " AND enabled = true " +                  
290                          "ORDER BY name ";                  try {
291                                                    pm = PMF.get().getPersistenceManager();
                         Connection conn = null;  
                         Statement stmt = null;  
                         ResultSet res = null;  
                         List<StationBean> result;  
292                                                    
293                          try {                          List oldEntries = (List) pm.newQuery(JdoStationBean.class).execute();
294                                  conn = DBConnection.getConnection();                          pm.deletePersistentAll(oldEntries);
295                                  stmt = conn.createStatement();                          
296                                  res = stmt.executeQuery(SQL);                          List<JdoStationBean> jdoList = new ArrayList<JdoStationBean>();
297                                  result = convertResultset(res);                          for (StationEntry station : stationBean.entries) {
298                          } finally {                                  JdoStationBean jdoBean = JdoStationBean.fromStationEntry(station);
299                                  if (res != null)                                  
300                                          res.close();                                  jdoList.add(jdoBean);
301                                  if (stmt != null)                                  
302                                          stmt.close();                          }
303                                  if (conn!= null)                          pm.makePersistentAll(jdoList);
304                                          conn.close();                          
305                          }                          return jdoList.size();
306                                                    
307                          return result;                  } finally {
308                                                    pm.close();
309           }                  }
310           public static String getStationName(int stationID) {          }
311                   String station = "";          
   
                  Connection conn = null;  
                  try {  
                          conn = DBConnection.getConnection();  
                          Statement stmt = conn.createStatement();  
                          ResultSet rs = stmt.executeQuery("SELECT name FROM trainstations WHERE id=" + stationID);  
                          if (rs.next()) {  
                                  station = rs.getString(1);  
                          }  
   
                  } catch (Exception e) {          
                  } finally {  
                          try {  
                                  if (conn != null && !conn.isClosed())  
                                          conn.close();  
                          } catch (Exception e) {}  
                  }  
   
                  return station;  
          }  
312  }  }

Legend:
Removed from v.737  
changed lines
  Added in v.1113

  ViewVC Help
Powered by ViewVC 1.1.20