AbstractMediaTypeCollection.java

  1. /*
  2.  * GovWay - A customizable API Gateway
  3.  * https://govway.org
  4.  *
  5.  * Copyright (c) 2005-2025 Link.it srl (https://link.it).
  6.  *
  7.  * This program is free software: you can redistribute it and/or modify
  8.  * it under the terms of the GNU General Public License version 3, as published by
  9.  * the Free Software Foundation.
  10.  *
  11.  * This program is distributed in the hope that it will be useful,
  12.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14.  * GNU General Public License for more details.
  15.  *
  16.  * You should have received a copy of the GNU General Public License
  17.  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
  18.  *
  19.  */

  20. package org.openspcoop2.message.config;

  21. import java.io.Serializable;
  22. import java.util.ArrayList;
  23. import java.util.List;

  24. import org.openspcoop2.message.constants.Costanti;
  25. import org.openspcoop2.message.constants.MessageType;
  26. import org.openspcoop2.message.exception.MessageException;
  27. import org.openspcoop2.utils.regexp.RegularExpressionEngine;
  28. import org.openspcoop2.utils.regexp.RegularExpressionPatternCompileMode;

  29. /**
  30.  * AbstractMediaTypeCollection
  31.  *
  32.  * @author Poli Andrea (apoli@link.it)
  33.  * @author $Author$
  34.  * @version $Rev$, $Date$
  35.  */
  36. public abstract class AbstractMediaTypeCollection implements Serializable {

  37.     /**
  38.      *
  39.      */
  40.     private static final long serialVersionUID = 1L;
  41.    
  42.     private static final int STATUS_DEFAULT = 0;
  43.     private static final String SEPARATORE = "__@@@__";
  44.     private static final int SEPARATORE_LEN = SEPARATORE.length();
  45.     private String buildKey(String mediaType, Integer status) {
  46.         if(status==null) {
  47.             status = STATUS_DEFAULT;
  48.         }
  49.         return status+SEPARATORE+mediaType;
  50.     }
  51.     private String extractMediaTypeFromKey(String key) {
  52.         int charIx =  key.indexOf( SEPARATORE );
  53.         return key.substring(charIx + SEPARATORE_LEN );
  54. //      return key.split(SEPARATORE)[1];
  55.     }
  56.     private int extractStatusFromKey(String key) {
  57.         int charIx =  key.indexOf( SEPARATORE );
  58.         return Integer.parseInt( key.substring(0, charIx) );
  59. //      return Integer.parseInt(key.split(SEPARATORE)[0]);
  60.     }
  61.    
  62.     // Vengono utilizzate due liste per preservare l'ordine di inserimento che si perde in una hashtable,
  63.     private List<String> map_status_mediaTypes = new ArrayList<>();
  64.     private List<MessageType> map_messageProcessor = new ArrayList<MessageType>();
  65.     private List<Boolean> map_useRegularExpression = new ArrayList<Boolean>();

  66.     public void addDefaultMediaType(MessageType version) throws MessageException{
  67.         this.addDefaultMediaType(null, version);
  68.     }
  69.     public void addUndefinedMediaType(MessageType version) throws MessageException{
  70.         this.addUndefinedMediaType(null, version);
  71.     }
  72.     public void addMediaType(String mediaType,MessageType version,boolean regExpr) throws MessageException{
  73.         this.addMediaType(mediaType, null, version, regExpr);
  74.     }
  75.     private void addDefaultMediaType(Integer status, MessageType version) throws MessageException{
  76.         this.addMediaType(Costanti.CONTENT_TYPE_ALL, status, version, false);
  77.     }
  78.     private void addUndefinedMediaType(Integer status, MessageType version) throws MessageException{
  79.         this.addMediaType(Costanti.CONTENT_TYPE_NOT_DEFINED, status, version, false);
  80.     }
  81.     private void addMediaType(String mediaType,Integer status, MessageType version,boolean regExpr) throws MessageException{
  82.         if(mediaType==null){
  83.             throw new MessageException("MediaType not defined");
  84.         }
  85.         if(version==null){
  86.             throw new MessageException("MessageProcessorVersion not defined");
  87.         }
  88.         String key = this.buildKey(mediaType, status);
  89.         if(this.map_status_mediaTypes.contains(key)){
  90.             String stato = "";
  91.             if(status!=null && STATUS_DEFAULT!=status.intValue()) {
  92.                 stato = " (http-status:"+status+")";
  93.             }
  94.             throw new MessageException("MediaType"+stato+" already defined for MessageProcessorVersion "+this.getMessageProcessorVersion(mediaType, status, false));
  95.         }
  96.         this.map_status_mediaTypes.add(key);
  97.         this.map_messageProcessor.add(version);
  98.         this.map_useRegularExpression.add(regExpr);
  99.     }
  100.    
  101.     public List<String> getContentTypes() {
  102.         List<String> l = new ArrayList<>();
  103.         for (String key : this.map_status_mediaTypes) {
  104.             String mediaType = extractMediaTypeFromKey(key);
  105.             if(l.contains(mediaType)==false) {
  106.                 l.add(mediaType);
  107.             }
  108.         }
  109.         return l;
  110.     }
  111.    
  112.     public void clear(){
  113.         this.map_status_mediaTypes.clear();
  114.         this.map_messageProcessor.clear();
  115.         this.map_useRegularExpression.clear();
  116.     }
  117.    
  118.     public void addOrReplaceMediaType(String mediaType,MessageType version,boolean regExpr) throws MessageException{
  119.         this.addOrReplaceMediaType(mediaType, null, version, regExpr);
  120.     }
  121.     public void addOrReplaceMediaType(String mediaType,Integer status,MessageType version,boolean regExpr) throws MessageException{
  122.         String key = this.buildKey(mediaType, status);
  123.         if(this.map_status_mediaTypes.contains(key)){
  124.             this.removeMediaType(mediaType,status);
  125.         }
  126.         this.addMediaType(mediaType, status, version, regExpr);
  127.     }
  128.    
  129.     public void removeMediaType(String mediaType) throws MessageException{
  130.         this.removeMediaType(mediaType, null);
  131.     }
  132.     public void removeMediaType(String mediaType,Integer status) throws MessageException{
  133.         String key = this.buildKey(mediaType, status);
  134.         int index = -1;
  135.         if(this.map_status_mediaTypes.contains(key)){
  136.             for (int i = 0; i < this.map_status_mediaTypes.size(); i++) {
  137.                 String keyCheck = this.map_status_mediaTypes.get(i);
  138.                 if(keyCheck.equals(key)){
  139.                     index = i;
  140.                     break;
  141.                 }
  142.             }
  143.         }
  144.         if(index>=0){
  145.             this.map_useRegularExpression.remove(index);
  146.             this.map_messageProcessor.remove(index);
  147.             this.map_status_mediaTypes.remove(index);
  148.         }
  149.     }
  150.    
  151.     public MessageType getMessageProcessor(String mediaType) throws MessageException{
  152.         return this.getMessageProcessor(mediaType, null);
  153.     }
  154.     public MessageType getMessageProcessor(String mediaType,Integer status) throws MessageException{
  155.         return this.getMessageProcessorVersion(mediaType, status, true);
  156.     }
  157.     private MessageType getMessageProcessorVersion(String mediaType,Integer status, boolean checkExpression) throws MessageException{
  158.        
  159.         if(status==null) {
  160.             status = STATUS_DEFAULT;
  161.         }
  162.        
  163.         for (int i = 0; i < this.map_status_mediaTypes.size(); i++) {
  164.            
  165.             String keyCheck = this.map_status_mediaTypes.get(i);
  166.             int statusCheck = this.extractStatusFromKey(keyCheck);
  167.             if(statusCheck!=status.intValue()) {
  168.                 continue;
  169.             }
  170.            
  171.             String mediaTypeCheck = this.extractMediaTypeFromKey(keyCheck);
  172.             MessageType mt = this._getMessageProcessorVersionEngine(checkExpression, i, mediaType, mediaTypeCheck);
  173.             if(mt!=null) {
  174.                 return mt;
  175.             }
  176.            
  177.         }  
  178.        
  179.         // provo a cercare sugli stati uguali a default
  180.         if(status.intValue()!=STATUS_DEFAULT) {
  181.        
  182.             for (int i = 0; i < this.map_status_mediaTypes.size(); i++) {
  183.                
  184.                 String keyCheck = this.map_status_mediaTypes.get(i);
  185.                 int statusCheck = this.extractStatusFromKey(keyCheck);
  186.                 if(statusCheck==STATUS_DEFAULT) {
  187.                     String mediaTypeCheck = this.extractMediaTypeFromKey(keyCheck);
  188.                     MessageType mt = this._getMessageProcessorVersionEngine(checkExpression, i, mediaType, mediaTypeCheck);
  189.                     if(mt!=null) {
  190.                         return mt;
  191.                     }
  192.                 }
  193.                
  194.             }
  195.            
  196.         }
  197.        
  198.         return null; // ritorno anzi null per gestire la differenza rispetto all'eccezione sopra
  199.     }
  200.     private MessageType _getMessageProcessorVersionEngine(boolean checkExpression, int i, String mediaType, String mediaTypeCheck) throws MessageException {
  201.         if(checkExpression){
  202.             if(this.map_useRegularExpression.get(i)){
  203.                 if(mediaType==null){
  204.                     return null;
  205.                 }
  206.                 String pattern = mediaTypeCheck;
  207.                 try{
  208.                     if(RegularExpressionEngine.isMatch(mediaType, pattern, RegularExpressionPatternCompileMode.CASE_INSENSITIVE)){
  209.                         return this.map_messageProcessor.get(i);
  210.                     }
  211.                 }catch(Exception e){
  212.                     throw new MessageException("Errore durante l'identificazione del content-type ["+mediaType+"] (pattern:"+pattern+"): "+e.getMessage(),e);
  213.                 }
  214.             }
  215.             else{
  216.                 if(Costanti.CONTENT_TYPE_ALL.equals(mediaTypeCheck)){
  217.                     return this.map_messageProcessor.get(i);
  218.                 }
  219.                 else if(Costanti.CONTENT_TYPE_NOT_DEFINED.equals(mediaTypeCheck) &&
  220.                         (mediaType==null || "".equals(mediaType.trim()))){
  221.                     return this.map_messageProcessor.get(i);
  222.                 }
  223.                 else if(mediaTypeCheck.equals(mediaType)){
  224.                     return this.map_messageProcessor.get(i);
  225.                 }
  226.             }
  227.         }
  228.         else{
  229.             if(mediaTypeCheck.equals(mediaType)){
  230.                 return this.map_messageProcessor.get(i);
  231.             }
  232.         }
  233.         return null;
  234.     }
  235. }