package me.chenyi.mm.service; import java.io.File; import java.net.URL; import java.net.URLEncoder; import java.sql.Connection; import java.util.*; import java.util.logging.Logger; import com.moviejukebox.themoviedb.IMovieService; import com.moviejukebox.themoviedb.MovieDbException; import com.moviejukebox.themoviedb.TheMovieDb; import com.moviejukebox.themoviedb.model.MovieDb; import com.moviejukebox.themoviedb.model.TmdbConfiguration; import me.chenyi.mm.MovieManager; import me.chenyi.mm.model.*; import me.chenyi.mm.util.FileUtil; import me.chenyi.mm.util.SysUtil; /** * Class description goes here * * @author $Author:$ * @version $Revision:$ */ public class ServiceUtilities { private static Logger logger = Logger.getLogger(ServiceUtilities.class.getName()); private static final String API_KEY; private static IMovieService movieService; static { String configApiKey = MovieManager.getConfig().getConfig("apiKey"); API_KEY = configApiKey == null? "5a1a77e2eba8984804586122754f969f": configApiKey; } public static List<String> initMovieService() { try { movieService = new TheMovieDb(API_KEY); } catch (Exception e) { e.printStackTrace(); return Collections.singletonList(e.getMessage()); } return Collections.emptyList(); } //you can implement any movie service you want, for example, IMDB public static void setMovieService(IMovieService movieService) { ServiceUtilities.movieService = movieService; } public static Map<String, Map<String, Class>> getNodeTypeAttributeMap() { return movieService.getNodeTypeAttributeMap(); } public static List<String> getImageSizeList(String imageType) { TmdbConfiguration configuration = movieService.getConfiguration(); if (imageType.equalsIgnoreCase(ImageType.backdrop.toString())) { return configuration.getBackdropSizes(); } else if (imageType.equalsIgnoreCase(ImageType.logo.toString())) { return configuration.getLogoSizes(); } else if (imageType.equalsIgnoreCase(ImageType.poster.toString())) { return configuration.getPosterSizes(); } else if (imageType.equalsIgnoreCase(ImageType.profile.toString())) { return configuration.getProfileSizes(); } return Collections.emptyList(); } public static Map<String, String> getImageFileMap(String movieTitle, String imageType) { Map<String, String> result = new HashMap<String, String>(); List<String> sizeList = getImageSizeList(imageType); for (String sizeStr : sizeList) { String attrName = imageType + "_" + sizeStr; try { String imageFileName = URLEncoder.encode(movieTitle + "_" + attrName + ".jpg", "UTF8"); result.put(attrName, imageFileName); } catch(Exception e) { e.printStackTrace(); } } return result; } /** * return image file path mapping. * @param imageUrl the image url in tmdb api * @param imageType which type: backdrop / poster for movie, logo / profile for ? * @return mapping contains image file information, * key: attribute name, consist with imageType and sizeInfo (imageType_sizeInfo) * value: image url in TMDB site, like '' */ public static Map<String, String> getImageUrlMap(String imageUrl, String imageType) { Map<String, String> result = new HashMap<String, String>(); TmdbConfiguration configuration = movieService.getConfiguration(); List<String> sizeList = getImageSizeList(imageType); String baseUrl = configuration.getBaseUrl(); for (String sizeStr : sizeList) { result.put(imageType + "_" + sizeStr, baseUrl + "/" + sizeStr + "/" + imageUrl); } return result; } private static void downloadImage(Connection connection,String movieTitle, String urlPath, String imageType, Map valueMap) { if (urlPath == null || connection == null || movieTitle == null || imageType == null) return; Map<String, String> imageUrlMap = getImageUrlMap(urlPath, imageType); String size = MovieManager.getConfig().getConfig(imageType + "_size"); if (size == null) { List<String> imageSizeList = getImageSizeList(imageType); if (imageSizeList == null || imageSizeList.size() == 0) return; size = imageSizeList.get(0); if (size == null) return; } Map<String, String> posterFilePathList = getImageFileMap(movieTitle, imageType); for (String attrName : imageUrlMap.keySet()) { if (attrName.endsWith(size)) { String url = imageUrlMap.get(attrName); String imageFileName = posterFilePathList.get(attrName); try { FileUtil.downloadToFile(new URL(url), new File( SysUtil.getConfigDir().getAbsolutePath() + "/image/" + imageFileName)); if (valueMap != null) valueMap.put(ModelUtils.getOrAddAttribute(connection, attrName, Attribute.AttributeType.File), imageFileName); return; } catch(Exception e) { e.printStackTrace(); } } } } public static void addMovieInfoToDatabase(long movieId, boolean update) { MovieDb movieDb = null; try { movieDb = movieService.getMovieInfo(movieId, ""); } catch(Exception e) { e.printStackTrace(); return; } if (movieDb == null) { logger.warning(String.format("updateMovieInfoToDatabase: movieDb == null for id: %s", movieId)); return; } Connection connection = null; try { connection = DatabaseUtil.openConnection(); String movieTitle = movieDb.getTitle(); long tmdbId = movieDb.getId(); Map<Attribute, Object> valueMap = new HashMap(); Map<String, Object> movieDbValueMap = movieDb.getValueMap(); for(String attributeName : movieDbValueMap.keySet()) { Object value = movieDbValueMap.get(attributeName); if (value == null) continue; Attribute.AttributeType type = Attribute.AttributeType.String; if(value instanceof Number) { type = Attribute.AttributeType.Number; } else value = String.valueOf(value); valueMap.put(ModelUtils.getOrAddAttribute(connection, attributeName, type), value); } downloadImage(connection, movieTitle, movieDb.getPosterPath(), ImageType.poster.toString(), valueMap); downloadImage(connection, movieTitle, movieDb.getBackdropPath(), ImageType.backdrop.toString(), valueMap); Node node = ModelUtils.searchMovieByTmdbId(tmdbId); //see if the node already exist. if (node != null) { if (update) ModelUtils.updateNode(connection, movieId, valueMap); else { logger.warning(String.format("Node already exist for id: %s, title: %s", movieId, movieTitle)); } } else { ModelUtils.addMovie(connection, valueMap); } } catch(Exception e) { e.printStackTrace(); } finally { if (connection != null) { DatabaseUtil.closeConnection(connection); } } } public static List<MovieDb> searchMovie(String name) { try { return movieService.searchMovie(name, "", true); } catch(MovieDbException e) { e.printStackTrace(); } return Collections.emptyList(); } public static void addMovieInfoToDatabase(String name, int maxCount, boolean update) { try { List<MovieDb> movieDbList = movieService.searchMovie(name, "", true); if (movieDbList == null || movieDbList.size() == 0) return; if (maxCount <= 0) maxCount = Integer.MAX_VALUE; Connection connection = DatabaseUtil.openConnection(); for(int i = 0; i < Math.min(movieDbList.size(), maxCount); i ++) { MovieDb movieDb = movieDbList.get(i); //search movie does not return all Movie info //this is to get full movie info //todo: is this correct? movieDb = movieService.getMovieInfo(movieDb.getId(), ""); String movieTitle = movieDb.getTitle(); long tmdbId = movieDb.getId(); Map<Attribute, Object> valueMap = new HashMap(); Map<String, Object> movieDbValueMap = movieDb.getValueMap(); for(String attributeName : movieDbValueMap.keySet()) { Object value = movieDbValueMap.get(attributeName); if(value == null) continue; Attribute.AttributeType type = Attribute.AttributeType.String; if(value instanceof Number) { type = Attribute.AttributeType.Number; } else value = String.valueOf(value); valueMap.put(ModelUtils.getOrAddAttribute(connection, attributeName, type), value); } downloadImage(connection, movieTitle, movieDb.getPosterPath(), ImageType.poster.toString(), valueMap); downloadImage(connection, movieTitle, movieDb.getBackdropPath(), ImageType.backdrop.toString(), valueMap); Node node = ModelUtils.searchMovieByTmdbId(tmdbId); //see if the node already exist. if(node != null) { if (update) { ModelUtils.updateNode(connection, tmdbId, valueMap); } else { logger.warning(String.format("Node already exist for %s", movieTitle)); continue; } } else { ModelUtils.addMovie(connection, valueMap); } } DatabaseUtil.closeConnection(connection); } catch(Exception e) { e.printStackTrace(); } } }