View Javadoc
1   /*
2    * Copyright 2010 James Pether Sörling
3    *
4    * Licensed under the Apache License, Version 2.0 (the "License");
5    * you may not use this file except in compliance with the License.
6    * You may obtain a copy of the License at
7    *
8    *   http://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS,
12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13   * See the License for the specific language governing permissions and
14   * limitations under the License.
15   *
16   *	$Id$
17   *  $HeadURL$
18  */
19  package com.hack23.cia.service.external.vdem.impl;
20  
21  import java.io.IOException;
22  import java.io.InputStreamReader;
23  import java.io.Reader;
24  import java.net.URL;
25  import java.util.ArrayList;
26  import java.util.Iterator;
27  import java.util.List;
28  
29  import org.apache.commons.csv.CSVFormat;
30  import org.apache.commons.csv.CSVParser;
31  import org.apache.commons.csv.CSVRecord;
32  import org.apache.poi.ss.usermodel.Row;
33  import org.apache.poi.xssf.usermodel.XSSFSheet;
34  import org.apache.poi.xssf.usermodel.XSSFWorkbook;
35  import org.slf4j.Logger;
36  import org.slf4j.LoggerFactory;
37  import org.springframework.stereotype.Service;
38  import org.springframework.util.StringUtils;
39  
40  import com.hack23.cia.model.external.vdem.indicators.impl.CountryQuestionData;
41  import com.hack23.cia.model.external.vdem.indicators.impl.CountryQuestionDataEmbeddedId;
42  import com.hack23.cia.model.external.vdem.indicators.impl.Question;
43  import com.hack23.cia.service.external.vdem.api.VdemService;
44  
45  /**
46   * The Class VdemServiceImpl.
47   */
48  @Service
49  public final class VdemServiceImpl implements VdemService {
50  
51  	/** The Constant VDEM_DATA_DOWNLOAD_URL. */
52  	private static final String VDEM_DATA_DOWNLOAD_URL = "https://s3-eu-west-1.amazonaws.com/vdemdata/V-Dem-DS-CY-v5.csv";
53  
54  	/** The Constant LOGGER. */
55  	private static final Logger LOGGER = LoggerFactory.getLogger(VdemServiceImpl.class);
56  
57  	@Override
58  	public List<Question> getQuestions() {
59  
60  		final List<Question> list = new ArrayList<>();
61  		try {
62  			final XSSFWorkbook myWorkBook = new XSSFWorkbook(VdemServiceImpl.class.getResourceAsStream("/V-DemQuestionIDsv5(2016).xlsx"));
63  			final XSSFSheet mySheet = myWorkBook.getSheetAt(0);
64  			final Iterator<Row> rowIterator = mySheet.iterator();
65  
66  			rowIterator.next();
67  
68  			while (rowIterator.hasNext()) {
69  				final Row row = rowIterator.next();
70  
71  				final Question question = new Question();
72  
73  				if (row.getCell(0) == null) {
74  					question.setTag(row.getCell(1).toString());
75  					question.setName(row.getCell(2).toString());
76  				} else {
77  					question.setQuestionId(row.getCell(0).toString());
78  					question.setTag(row.getCell(1).toString());
79  					question.setName(row.getCell(2).toString());
80  				}
81  				list.add(question);
82  			}
83  
84  			myWorkBook.close();
85  		} catch (final IOException e) {
86  			LOGGER.warn("Problem loading", e);
87  		}
88  
89  		return list;
90  
91  	}
92  
93  	/**
94  	 * Gets the country question data.
95  	 *
96  	 * @return the country question data
97  	 */
98  	@Override
99  	public List<CountryQuestionData> getCountryQuestionData() {
100 		final List<CountryQuestionData> list = new ArrayList<>();
101 
102 		final List<Question> questions = getQuestions();
103 
104 		try {
105 			final Reader in = new InputStreamReader(new URL(VDEM_DATA_DOWNLOAD_URL).openStream());
106 
107 			final CSVParser parser = new CSVParser(in, CSVFormat.EXCEL.withHeader().withDelimiter(','));
108 
109 			for (final CSVRecord record : parser) {
110 				final String countryName = record.get("country_name");
111 				final String countryId = record.get("country_id");
112 				final String countryTextId = record.get("country_text_id");
113 				final String year = record.get("year");
114 				final String gapStart = record.get("gapstart");
115 				final String gapEnd = record.get("gapend");
116 				final String codingEnd = record.get("codingend");
117 				final String cowCode = record.get("COWcode");
118 
119 				final int currentSize = list.size();
120 				LOGGER.info("Loading vdem data for country:{} year {} ",countryName,year);
121 
122 				for (final Question question : questions) {
123 					addQuestionDataToList(list, record, countryName, countryId, countryTextId, year, gapStart, gapEnd,
124 							codingEnd, cowCode, question);
125 				}
126 
127 				final int afterSize = list.size();
128 				LOGGER.info("Found vdem data for country:{} year:{} data points:{}",countryName,year,afterSize -currentSize);
129 
130 			}
131 			parser.close();
132 
133 		} catch (final IOException e) {
134 
135 			LOGGER.warn("Problem loading vdem data", e);
136 		}
137 
138 		return list;
139 	}
140 
141 	/**
142 	 * Adds the question data to list.
143 	 *
144 	 * @param list
145 	 *            the list
146 	 * @param record
147 	 *            the record
148 	 * @param countryName
149 	 *            the country name
150 	 * @param countryId
151 	 *            the country id
152 	 * @param countryTextId
153 	 *            the country text id
154 	 * @param year
155 	 *            the year
156 	 * @param gapStart
157 	 *            the gap start
158 	 * @param gapEnd
159 	 *            the gap end
160 	 * @param codingEnd
161 	 *            the coding end
162 	 * @param cowCode
163 	 *            the cow code
164 	 * @param question
165 	 *            the question
166 	 */
167 	private static void addQuestionDataToList(final List<CountryQuestionData> list, final CSVRecord record,
168 			final String countryName, final String countryId, final String countryTextId, final String year,
169 			final String gapStart, final String gapEnd, final String codingEnd, final String cowCode,
170 			final Question question) {
171 		if (question.getQuestionId() != null) {
172 
173 			if (record.isMapped(question.getTag())) {
174 
175 				try {
176 					final String questionValue = record.get(question.getTag());
177 
178 					if (questionValue != null && StringUtils.hasText(questionValue)) {
179 						final CountryQuestionData countryQuestionData = new CountryQuestionData();
180 						final CountryQuestionDataEmbeddedId embeddedId = new CountryQuestionDataEmbeddedId();
181 
182 						embeddedId.setCountryName(countryName);
183 						embeddedId.setCountryId(countryId);
184 						embeddedId.setIndicatorId(question.getTag());
185 						embeddedId.setYear(Integer.parseInt(year));
186 						embeddedId.setCountryId(countryId);
187 
188 						countryQuestionData.setEmbeddedId(embeddedId);
189 
190 						countryQuestionData.setCountryTextId(countryTextId);
191 						countryQuestionData.setGapstart(gapStart);
192 						countryQuestionData.setGapend(gapEnd);
193 						countryQuestionData.setCodingend(codingEnd);
194 						countryQuestionData.setCowCode(cowCode);
195 						countryQuestionData.setQuestionValue(questionValue.trim());
196 
197 						list.add(countryQuestionData);
198 					}
199 				} catch (final RuntimeException e) {
200 					LOGGER.warn("Missing value for:"+ question.getTag(), e);
201 				}
202 			}
203 		}
204 	}
205 
206 }