001/* 002 * Copyright 2017 Anyware Services 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016package org.ametys.plugins.repository.metadata; 017 018import java.util.Collections; 019import java.util.LinkedHashMap; 020import java.util.List; 021import java.util.Locale; 022import java.util.Map; 023import java.util.Set; 024 025import org.apache.commons.lang3.LocaleUtils; 026 027import org.ametys.plugins.repository.AmetysRepositoryException; 028 029/** 030 * Helper methods for {@link MultilingualString} metadata 031 */ 032public final class MultilingualStringHelper 033{ 034 /** The default locale */ 035 public static final Locale DEFAULT_LOCALE = Locale.ENGLISH; 036 037 private MultilingualStringHelper() 038 { 039 // Hide default constructor. 040 } 041 042 /** 043 * Returns the closest non-empty value for a {@link MultilingualString} metadata in a given locale. 044 * If no close locale is found, return the value for {@link Locale#ENGLISH} if exists.<br> 045 * Otherwise, the value of first stored locale will be returned.<br> 046 * @param parentMetadata The metadata holder 047 * @param metadataName The metadata name 048 * @param locale The requested locale 049 * @return the closest non-empty localized value or <code>null</code> if not found. 050 * @throws AmetysRepositoryException if an errors occurs. 051 */ 052 public static String getValue(CompositeMetadata parentMetadata, String metadataName, Locale locale) throws AmetysRepositoryException 053 { 054 if (parentMetadata.hasMetadata(metadataName)) 055 { 056 MultilingualString multilingualString = parentMetadata.getMultilingualString(metadataName); 057 058 return getValue(multilingualString, locale); 059 } 060 061 return null; 062 } 063 064 /** 065 * Returns the closest non-empty value for a {@link MultilingualString} in a given locale. 066 * If no close locale is found, return the value for {@link Locale#ENGLISH} if exists.<br> 067 * Otherwise, the value of first stored locale will be returned.<br> 068 * @param multilingualString The multilingual string 069 * @param locale The requested locale. Can be null. 070 * @return the closest non-empty localized value or <code>null</code> if not found. 071 * @throws AmetysRepositoryException if an errors occurs. 072 */ 073 public static String getValue(MultilingualString multilingualString, Locale locale) throws AmetysRepositoryException 074 { 075 if (locale != null && multilingualString.hasLocale(locale)) 076 { 077 return multilingualString.getValue(locale); 078 } 079 else 080 { 081 // Try to find the closest locale 082 List<Locale> closedLocales = localeLookupList(locale); 083 for (Locale closedLocale : closedLocales) 084 { 085 if (multilingualString.hasLocale(closedLocale)) 086 { 087 return multilingualString.getValue(closedLocale); 088 } 089 } 090 091 // No locale found, get the first stored locale 092 Set<Locale> allLocales = multilingualString.getLocales(); 093 if (!allLocales.isEmpty()) 094 { 095 Locale firstLocale = allLocales.iterator().next(); 096 return multilingualString.getValue(firstLocale); 097 } 098 099 return null; 100 } 101 } 102 103 /** 104 * Return the list of closest locales to search 105 * @param locale the locale to start from. If null, returns the default locale 106 * @return the unmodifiable list of Locale objects, 0 being locale, not null 107 */ 108 public static List<Locale> localeLookupList(Locale locale) 109 { 110 if (locale != null) 111 { 112 return LocaleUtils.localeLookupList(locale, DEFAULT_LOCALE); 113 } 114 else 115 { 116 return Collections.singletonList(DEFAULT_LOCALE); 117 } 118 } 119 120 /** 121 * Get the JSON representation of a {@link MultilingualString} 122 * @param multilingualString The multilingual string. Cannot be null. 123 * @return A map with the locales and values. 124 * @throws AmetysRepositoryException if an error occurs 125 */ 126 public static Map<String, Object> toJson(MultilingualString multilingualString) throws AmetysRepositoryException 127 { 128 Map<String, Object> json = new LinkedHashMap<>(); 129 130 for (Locale locale : multilingualString.getLocales()) 131 { 132 json.put(locale.toString(), multilingualString.getValue(locale)); 133 } 134 135 return json; 136 } 137}