You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

DefaultCommonServices.java 6.4KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198
  1. package org.apache.archiva.rest.services;
  2. /*
  3. * Licensed to the Apache Software Foundation (ASF) under one
  4. * or more contributor license agreements. See the NOTICE file
  5. * distributed with this work for additional information
  6. * regarding copyright ownership. The ASF licenses this file
  7. * to you under the Apache License, Version 2.0 (the
  8. * "License"); you may not use this file except in compliance
  9. * with the License. You may obtain a copy of the License at
  10. *
  11. * http://www.apache.org/licenses/LICENSE-2.0
  12. *
  13. * Unless required by applicable law or agreed to in writing,
  14. * software distributed under the License is distributed on an
  15. * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
  16. * KIND, either express or implied. See the License for the
  17. * specific language governing permissions and limitations
  18. * under the License.
  19. */
  20. import org.apache.archiva.components.scheduler.CronExpressionValidator;
  21. import org.apache.archiva.redback.rest.api.services.RedbackServiceException;
  22. import org.apache.archiva.redback.rest.api.services.UtilServices;
  23. import org.apache.archiva.rest.api.model.ActionStatus;
  24. import org.apache.archiva.rest.api.model.ValidationStatus;
  25. import org.apache.archiva.rest.api.services.ArchivaRestServiceException;
  26. import org.apache.archiva.rest.api.services.CommonServices;
  27. import org.apache.commons.lang3.StringUtils;
  28. import org.slf4j.Logger;
  29. import org.slf4j.LoggerFactory;
  30. import org.springframework.stereotype.Service;
  31. import javax.annotation.PostConstruct;
  32. import javax.inject.Inject;
  33. import javax.validation.Valid;
  34. import javax.ws.rs.core.Response;
  35. import java.io.ByteArrayInputStream;
  36. import java.io.IOException;
  37. import java.io.InputStream;
  38. import java.util.Map;
  39. import java.util.Properties;
  40. import java.util.concurrent.ConcurrentHashMap;
  41. /**
  42. * @author Olivier Lamy
  43. */
  44. @Service("commonServices#rest")
  45. public class DefaultCommonServices
  46. implements CommonServices
  47. {
  48. private static final String RESOURCE_NAME = "org/apache/archiva/i18n/default";
  49. private Logger log = LoggerFactory.getLogger( getClass() );
  50. @Inject
  51. private UtilServices utilServices;
  52. private Map<String, String> cachei18n = new ConcurrentHashMap<String, String>();
  53. @Inject
  54. protected CronExpressionValidator cronExpressionValidator;
  55. @PostConstruct
  56. public void init()
  57. throws ArchivaRestServiceException
  58. {
  59. // preload i18n en and fr
  60. getAllI18nResources( "en" );
  61. getAllI18nResources( "fr" );
  62. }
  63. @Override
  64. public String getI18nResources( String locale )
  65. throws ArchivaRestServiceException
  66. {
  67. Properties properties = new Properties();
  68. StringBuilder resourceName = new StringBuilder( RESOURCE_NAME );
  69. try
  70. {
  71. loadResource( properties, resourceName, locale );
  72. }
  73. catch ( IOException e )
  74. {
  75. log.warn( "skip error loading properties {}", resourceName );
  76. }
  77. return fromProperties( properties );
  78. }
  79. private void loadResource( Properties properties, StringBuilder resourceName, String locale )
  80. throws IOException
  81. {
  82. // load default
  83. loadResource( properties, new StringBuilder( resourceName ).append( ".properties" ).toString(), locale );
  84. // if locale override with locale content
  85. if ( StringUtils.isNotEmpty( locale ) )
  86. {
  87. loadResource( properties,
  88. new StringBuilder( resourceName ).append( "_" + locale ).append( ".properties" ).toString(),
  89. locale );
  90. }
  91. }
  92. private String fromProperties( final Properties properties )
  93. {
  94. StringBuilder output = new StringBuilder();
  95. for ( Map.Entry<Object, Object> entry : properties.entrySet() )
  96. {
  97. output.append( (String) entry.getKey() ).append( '=' ).append( (String) entry.getValue() );
  98. output.append( '\n' );
  99. }
  100. return output.toString();
  101. }
  102. private void loadResource( final Properties finalProperties, String resourceName, String locale )
  103. throws IOException
  104. {
  105. Properties properties = new Properties();
  106. try (InputStream is = Thread.currentThread().getContextClassLoader().getResourceAsStream( resourceName ))
  107. {
  108. if ( is != null )
  109. {
  110. properties.load( is );
  111. finalProperties.putAll( properties );
  112. }
  113. else
  114. {
  115. if ( !StringUtils.equalsIgnoreCase( locale, "en" ) )
  116. {
  117. log.info( "cannot load resource {}", resourceName );
  118. }
  119. }
  120. }
  121. }
  122. @Override
  123. public String getAllI18nResources( String locale )
  124. throws ArchivaRestServiceException
  125. {
  126. String cachedi18n = cachei18n.get( StringUtils.isEmpty( locale ) ? "en" : StringUtils.lowerCase( locale ) );
  127. if ( cachedi18n != null )
  128. {
  129. return cachedi18n;
  130. }
  131. try
  132. {
  133. Properties all = utilServices.getI18nProperties( locale );
  134. StringBuilder resourceName = new StringBuilder( RESOURCE_NAME );
  135. loadResource( all, resourceName, locale );
  136. String i18n = fromProperties( all );
  137. cachei18n.put( StringUtils.isEmpty( locale ) ? "en" : StringUtils.lowerCase( locale ), i18n );
  138. return i18n;
  139. }
  140. catch ( IOException e )
  141. {
  142. throw new ArchivaRestServiceException( e.getMessage(),
  143. Response.Status.INTERNAL_SERVER_ERROR.getStatusCode(), e );
  144. }
  145. catch ( RedbackServiceException e )
  146. {
  147. throw new ArchivaRestServiceException( e.getMessage(), e.getHttpErrorCode(), e );
  148. }
  149. }
  150. private void loadFromString( String propsStr, Properties properties )
  151. throws ArchivaRestServiceException
  152. {
  153. try (InputStream inputStream = new ByteArrayInputStream( propsStr.getBytes() ))
  154. {
  155. properties.load( inputStream );
  156. }
  157. catch ( IOException e )
  158. {
  159. throw new ArchivaRestServiceException( e.getMessage(),
  160. Response.Status.INTERNAL_SERVER_ERROR.getStatusCode(), e );
  161. }
  162. }
  163. @Override
  164. public ValidationStatus validateCronExpression( String cronExpression )
  165. throws ArchivaRestServiceException
  166. {
  167. return new ValidationStatus(cronExpressionValidator.validate( cronExpression ));
  168. }
  169. }