Commit 7b936beb authored by Matija Obreza's avatar Matija Obreza
Browse files

Country and Geo services

parent 521f04e0
/**
* Copyright 2013 Global Crop Diversity Trust
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
**/
package org.crophub.rest.common.model.impl;
import java.text.MessageFormat;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
@Entity
@Table(name = "country")
public class Country implements java.io.Serializable {
private static final long serialVersionUID = -1688723909298769804L;
private Long id;
private String code3;
private String code2;
private boolean current;
private String name;
private String codeNum;
private Long refnameId;
public Country() {
}
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
@Column(unique = true, nullable = false)
public Long getId() {
return this.id;
}
public void setId(final Long id) {
this.id = id;
}
@Column(nullable = false, unique = true, length = 3)
public String getCode3() {
return code3;
}
public void setCode3(final String code3) {
this.code3 = code3;
}
@Column(unique=false, length = 2)
public String getCode2() {
return this.code2;
}
public void setCode2(final String code2) {
this.code2 = code2;
}
@Column
public boolean isCurrent() {
return this.current;
}
public void setCurrent(final boolean current) {
this.current = current;
}
@Column(unique = false, nullable = false, length = 200)
public String getName() {
return this.name;
}
public void setName(final String name) {
this.name = name;
}
@Column(length = 3)
public void setCodeNum(final String isoNum) {
this.codeNum = isoNum;
}
public String getCodeNum() {
return codeNum;
}
public void setRefnameId(final Long refnameId) {
this.refnameId = refnameId;
}
public Long getRefnameId() {
return refnameId;
}
@Override
public String toString() {
return MessageFormat.format("Country id={0} name={1} current={2}", id,
name, current);
}
}
/**
* Copyright 2013 Global Crop Diversity Trust
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
**/
package org.crophub.rest.common.persistence.domain;
import java.util.List;
import org.crophub.rest.common.model.impl.Country;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.Modifying;
import org.springframework.data.jpa.repository.Query;
public interface CountryRepository extends JpaRepository<Country, Long> {
Country findByName(String name);
// @Query("from Country c where c.code3= ?1 and c.current=true")
Country findByCode3(String code3);
Country findByCode2(String code2);
// List<Country> findByRegion(Region region);
@Query("from Country c where c.current=false")
List<Country> findInactive();
Page<Country> findByCurrent(boolean current, Pageable pageable);
@Modifying
@Query("update Country c set c.current=false")
void deactivateAll();
// @Query("select distinct c from Country c where c.region in ( ?1 )")
// List<Country> findByRegions(List<Region> regions);
}
/**
* Copyright 2013 Global Crop Diversity Trust
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
**/
package org.crophub.rest.common.service;
import java.io.IOException;
import java.util.List;
import org.crophub.rest.common.model.impl.Country;
public interface GeoService {
// List<Region> findAllSubregions(Region region);
//
// List<Country> findAllCountriesInRegion(Region region);
//
// List<Region> findContinents();
/**
* Update ISO countries
*
* @throws IOException
*/
void updateCountryData() throws IOException;
Country getCountry(String iso3);
List<Country> listAll();
}
/**
* Copyright 2013 Global Crop Diversity Trust
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
**/
package org.crophub.rest.common.service.impl;
import java.io.IOException;
import java.util.List;
import org.apache.commons.lang.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.crophub.rest.common.model.impl.Country;
import org.crophub.rest.common.persistence.domain.CountryRepository;
import org.crophub.rest.common.service.GeoService;
import org.croptrust.geo.sources.CountryInfo;
import org.croptrust.geo.sources.DavrosCountrySource;
import org.croptrust.geo.sources.GeoNamesCountrySource;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
@Service
@Transactional(readOnly = true)
public class GeoServiceImpl implements GeoService {
public static final Log LOG = LogFactory.getLog(GeoServiceImpl.class);
@Autowired
CountryRepository countryRepository;
@Override
public List<Country> listAll() {
return countryRepository.findAll(new Sort("name", "current"));
}
@Override
public Country getCountry(String countryString) {
Country country = null;
if (countryString.length() == 3) {
country = countryRepository.findByCode3(countryString);
} else if (countryString.length() == 2) {
country = countryRepository.findByCode2(countryString);
}
return country != null ? country : countryRepository.findByName(countryString);
}
@Override
@Transactional(readOnly = false)
public void updateCountryData() throws IOException {
// update current countries
updateGeoNamesCountries();
// update from Davros, it has info on inactive country codes
updateDavrosCountries();
}
private void updateDavrosCountries() throws IOException {
final List<CountryInfo> countries = DavrosCountrySource.fetchCountryData();
if (LOG.isDebugEnabled()) {
LOG.debug("Got " + countries.size() + " countries from remote source.");
}
// check against repository
for (final CountryInfo countryInfo : countries) {
// Country country =
// countryRepository.findByName(countryInfo.getName());
final Country country = countryRepository.findByCode3(countryInfo.getIso3());
if (country == null) {
LOG.warn("Country " + countryInfo.getIso3() + " is not registered: " + countryInfo);
if (countryInfo.isActive()) {
LOG.warn("Country is marked as active. Should not be.");
}
final Country newCountry = new Country();
newCountry.setCode2(countryInfo.getIso());
newCountry.setCode3(countryInfo.getIso3());
newCountry.setCodeNum(countryInfo.getIsoNum());
newCountry.setCurrent(countryInfo.isActive());
newCountry.setName(countryInfo.getName());
countryRepository.save(newCountry);
LOG.info("Added country " + newCountry);
} else {
LOG.debug("Exists " + country);
// if iso2 is blank
if (StringUtils.isBlank(country.getCode2()) && StringUtils.isNotBlank(countryInfo.getIso())) {
LOG.info("Updating country iso2 code");
country.setCode2(countryInfo.getIso());
countryRepository.save(country);
}
// if iso-numeric is blank
if (StringUtils.isBlank(country.getCodeNum()) && StringUtils.isNotBlank(countryInfo.getIsoNum())) {
LOG.info("Updating country iso-numeric code");
country.setCodeNum(countryInfo.getIsoNum());
countryRepository.save(country);
}
/*
* // if all fields match if
* (country.getCode2().equals(countryInfo.getIso()) &&
* country.getCodeNum() != null &&
* country.getCodeNum().equals(countryInfo.getIsoNum())) { if
* (country.isCurrent() != countryInfo.isActive()) {
* LOG.warn("Country " + country + " is listed as active=" +
* countryInfo.isActive() + " on remote site");
* country.setCurrent(countryInfo.isActive());
* countryRepository.save(country); } }
*/
}
}
}
private void updateGeoNamesCountries() throws IOException {
final List<CountryInfo> countries = GeoNamesCountrySource.fetchCountryData();
if (LOG.isDebugEnabled()) {
LOG.debug("Got " + countries.size() + " countries from remote source.");
}
// deactivate all
countryRepository.deactivateAll();
// check against repository
for (final CountryInfo countryInfo : countries) {
final Country country = countryRepository.findByCode3(countryInfo.getIso3());
if (country == null) {
LOG.warn("Country " + countryInfo + " is not registered");
final Country newCountry = new Country();
newCountry.setCode2(countryInfo.getIso());
newCountry.setCode3(countryInfo.getIso3());
newCountry.setCodeNum(countryInfo.getIsoNum());
newCountry.setCurrent(countryInfo.isActive());
newCountry.setName(countryInfo.getName());
newCountry.setRefnameId(countryInfo.getRefnameId());
countryRepository.save(newCountry);
LOG.info("Added country " + newCountry);
} else {
LOG.debug("Exists " + country);
country.setCurrent(true);
country.setCode2(countryInfo.getIso());
country.setCodeNum(countryInfo.getIsoNum());
country.setName(countryInfo.getName());
country.setRefnameId(countryInfo.getRefnameId());
countryRepository.save(country);
/*
* // update refname id if (country.getRefnameId() == null &&
* countryInfo.getRefnameId() != null) {
* country.setRefnameId(countryInfo.getRefnameId());
* countryRepository.save(country); }
*
* // if country name is not the same if
* (StringUtils.isNotBlank(countryInfo.getName()) &&
* !countryInfo.getName().equals(country.getName())) {
*
* LOG.info("Updating country name from: " + country.getName() +
* " to: " + countryInfo.getName());
* country.setName(countryInfo.getName());
* countryRepository.save(country); }
*/
}
}
}
}
package org.crophub.rest.servlet.controller;
import org.crophub.rest.common.model.impl.Country;
import org.crophub.rest.common.service.GeoService;
import org.crophub.spring.ResourceNotFoundException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
@RequestMapping("/geo")
public class CountryController extends BaseController {
@Autowired
private GeoService geoService;
@RequestMapping
public String view(ModelMap model) {
model.addAttribute("countries", geoService.listAll());
return "/country/index";
}
@RequestMapping("/{country}")
public String view(ModelMap model, @PathVariable(value = "country") String countryStr) {
_logger.debug("Viewing country " + countryStr);
Country country = geoService.getCountry(countryStr);
if (country==null) {
throw new ResourceNotFoundException();
}
model.addAttribute("country", country);
return "/country/details";
}
}
......@@ -2,6 +2,7 @@ package org.crophub.rest.servlet.controller;
import org.crophub.rest.common.model.impl.Crop;
import org.crophub.rest.common.service.CropService;
import org.crophub.spring.ResourceNotFoundException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
......@@ -19,6 +20,9 @@ public class CropController extends BaseController {
public String view(ModelMap model, @PathVariable(value = "shortName") String shortName) {
_logger.debug("Viewing crop " + shortName);
Crop crop = cropService.getCrop(shortName);
if (crop == null) {
throw new ResourceNotFoundException();
}
model.addAttribute("crop", crop);
return "/crop/index";
}
......
......@@ -40,7 +40,7 @@ public class DatasetController extends BaseController {
@Autowired
private Validator validator;
@RequestMapping
@RequestMapping("/")
public String index(ModelMap model) {
List<Dataset> datasets = dataService.list();
model.addAttribute("datasets", datasets);
......
package org.crophub.spring;
import org.springframework.http.HttpStatus;
import org.springframework.web.bind.annotation.ResponseStatus;
@ResponseStatus(value = HttpStatus.NOT_FOUND)
public class ResourceNotFoundException extends RuntimeException {
private static final long serialVersionUID = -3351336944403763100L;
}
\ No newline at end of file
/**
* Copyright 2013 Global Crop Diversity Trust
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
**/
package org.croptrust.geo.sources;
import java.io.Serializable;
import java.text.MessageFormat;
public class CountryInfo implements Serializable {
private static final long serialVersionUID = 518678720881886517L;
private final String iso, iso3, isoNum;
private final String name;
private final boolean active;
private final Long refnameId;
public CountryInfo(final String iso, final String iso3,
final String isoNum, final String name, final boolean active) {
this.iso = iso;
this.iso3 = iso3;
this.isoNum = isoNum;
this.name = name;
this.active = active;
this.refnameId = null;
}
public CountryInfo(final String iso, final String iso3,
final String isoNum, final String name, final Long refnameId,
final boolean active) {
this.iso = iso;
this.iso3 = iso3;
this.isoNum = isoNum;
this.name = name;
this.active = active;
this.refnameId = refnameId;
}
public String getIso() {
return iso;
}
public String getIso3() {
return iso3;
}
public String getIsoNum() {
return isoNum;
}
public String getName() {
return name;
}
public boolean isActive() {
return active;
}
public Long getRefnameId() {
return refnameId;
}
@Override
public int hashCode() {
final int prime = 31;
int result = 1;
result = prime * result + (iso == null ? 0 : iso.hashCode());
result = prime * result + (iso3 == null ? 0 : iso3.hashCode());
result = prime * result + (isoNum == null ? 0 : isoNum.hashCode());
return result;
}
@Override
public boolean equals(final Object obj) {
if (this == obj) {
return true;
}
if (obj == null) {
return false;
}
if (getClass() != obj.getClass()) {
return false;
}
final CountryInfo other = (CountryInfo) obj;
if (iso == null) {
if (other.iso != null) {
return false;
}
} else if (!iso.equals(other.iso)) {
return false;
}
if (iso3 == null) {
if (other.iso3 != null) {
return false;
}
} else if (!iso3.equals(other.iso3)) {
return false;
}
if (isoNum == null) {