View Javadoc
1   package fr.paris.lutece.plugins.aot.modules.declarationimmat.service;
2   
3   import java.security.cert.CertificateException;
4   import java.util.Collections;
5   
6   import javax.net.ssl.HostnameVerifier;
7   import javax.net.ssl.SSLContext;
8   import javax.net.ssl.SSLSession;
9   import javax.net.ssl.SSLSocketFactory;
10  import javax.net.ssl.TrustManager;
11  import javax.net.ssl.X509TrustManager;
12  
13  import org.apache.commons.lang.StringUtils;
14  
15  import com.google.gson.JsonElement;
16  import com.google.gson.JsonObject;
17  import com.google.gson.JsonParser;
18  import com.google.gson.JsonPrimitive;
19  
20  import fr.paris.lutece.plugins.aot.modules.declarationimmat.business.Authorization;
21  import fr.paris.lutece.plugins.aot.modules.declarationimmat.exceptions.AuthorizationMalformedException;
22  import fr.paris.lutece.plugins.aot.modules.declarationimmat.exceptions.AuthorizationNotFoundException;
23  import fr.paris.lutece.plugins.aot.modules.declarationimmat.exceptions.ExistingAuthorizationException;
24  import fr.paris.lutece.plugins.aot.modules.declarationimmat.exceptions.UnauthorizedAccessException;
25  import fr.paris.lutece.plugins.aot.modules.declarationimmat.utils.AOTConstants;
26  import fr.paris.lutece.plugins.aot.modules.declarationimmat.utils.JaxbJacksonObjectMapper;
27  import fr.paris.lutece.portal.service.util.AppLogService;
28  import fr.paris.lutece.portal.service.util.AppPropertiesService;
29  import okhttp3.CipherSuite;
30  import okhttp3.ConnectionSpec;
31  import okhttp3.MediaType;
32  import okhttp3.OkHttpClient;
33  import okhttp3.Request;
34  import okhttp3.RequestBody;
35  import okhttp3.Response;
36  import okhttp3.TlsVersion;
37  
38  public class SNDIService
39  {
40  
41      private static final String    SERVICE_URL  = AppPropertiesService.getProperty( "aot-declarationimmat.serviceUrl" );
42      private static final Boolean   ACTIVATE_SSL = StringUtils.trimToEmpty( AppPropertiesService.getProperty( "aot-declarationimmat.activateSSL" ) ).equals( "true" );
43  
44      private static final MediaType JSON         = MediaType.parse( "application/json; charset=utf-8" );
45  
46      private static OkHttpClient    _httpClient;
47  
48      private static OkHttpClient getHttpClient( )
49      {
50  
51          if ( _httpClient != null )
52          {
53              return _httpClient;
54          }
55  
56          if ( ACTIVATE_SSL )
57          {
58              ConnectionSpec spec = new ConnectionSpec.Builder( ConnectionSpec.MODERN_TLS ).tlsVersions( TlsVersion.TLS_1_2 )
59                      .cipherSuites( CipherSuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256, CipherSuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256, CipherSuite.TLS_DHE_RSA_WITH_AES_128_GCM_SHA256 ).build( );
60  
61              _httpClient = new OkHttpClient.Builder( ).connectionSpecs( Collections.singletonList( spec ) ).build( );
62          }
63          else
64          {
65              _httpClient = getUnsafeOkHttpClient( );
66          }
67  
68          return _httpClient;
69      }
70  
71      private static OkHttpClient getUnsafeOkHttpClient( )
72      {
73          try
74          {
75              // Create a trust manager that does not validate certificate chains
76              final TrustManager[] trustAllCerts = new TrustManager[] { new X509TrustManager( )
77              {
78                  @Override
79                  public void checkClientTrusted( java.security.cert.X509Certificate[] chain, String authType ) throws CertificateException
80                  {
81                      // no check necessary
82                  }
83  
84                  @Override
85                  public void checkServerTrusted( java.security.cert.X509Certificate[] chain, String authType ) throws CertificateException
86                  {
87                      // no check necessary
88                  }
89  
90                  @Override
91                  public java.security.cert.X509Certificate[] getAcceptedIssuers( )
92                  {
93                      return new java.security.cert.X509Certificate[] { };
94                  }
95              } };
96  
97              // Install the all-trusting trust manager
98              final SSLContext sslContext = SSLContext.getInstance( "SSL" );
99              sslContext.init( null, trustAllCerts, new java.security.SecureRandom( ) );
100             // Create an ssl socket factory with our all-trusting manager
101             final SSLSocketFactory sslSocketFactory = sslContext.getSocketFactory( );
102 
103             OkHttpClient.Builder builder = new OkHttpClient.Builder( );
104             builder.sslSocketFactory( sslSocketFactory, ( X509TrustManager ) trustAllCerts[0] );
105             builder.hostnameVerifier( new HostnameVerifier( )
106             {
107                 @Override
108                 public boolean verify( String hostname, SSLSession session )
109                 {
110                     return true;
111                 }
112             } );
113 
114             return builder.build( );
115         }
116         catch ( Exception e )
117         {
118             throw new RuntimeException( e );
119         }
120     }
121 
122     private Request.Builder getRequestBuilder( String endPoint )
123     {
124         Request.Builder requestBuilder = new Request.Builder( );
125         requestBuilder.url( SERVICE_URL + endPoint );
126 
127         return requestBuilder;
128     }
129 
130     private Request getPostRequest( String endPoint, RequestBody body )
131     {
132         return getRequestBuilder( endPoint ).post( body ).build( );
133     }
134 
135     public Authorization create( Authorization authorization ) throws Exception
136     {
137         RequestBody body = RequestBody.create( JSON, authorization.toJson( ) );
138 
139         Request request = getPostRequest( "/aot", body );
140 
141         AppLogService.info( "Sent request to /aot with body :" );
142         AppLogService.info( authorization.toJson( ) );
143 
144         Response response = getHttpClient( ).newCall( request ).execute( );
145 
146         JsonObject dataJson = validate( response );
147 
148         return getAuthorizationFromJson( dataJson );
149     }
150 
151     public Authorization cancel( Authorization authorization ) throws Exception
152     {
153         JsonObject jsonBody = new JsonObject( );
154         jsonBody.add( "aotNumber", new JsonPrimitive( authorization.getNumber( ) ) );
155         jsonBody.add( "originApplicationCode", new JsonPrimitive( authorization.getOriginApplicationCode( ) ) );
156 
157         RequestBody body = RequestBody.create( JSON, jsonBody.toString( ) );
158         Request request = getPostRequest( "/aot/cancel", body );
159 
160         AppLogService.info( "Sent request to /aot/cancel with body :" );
161         AppLogService.info( jsonBody.toString( ) );
162 
163         Response response = getHttpClient( ).newCall( request ).execute( );
164 
165         JsonObject dataJson = validate( response );
166 
167         return getAuthorizationFromJson( dataJson );
168 
169     }
170 
171     private JsonObject validate( Response response ) throws Exception
172     {
173         String rawData = response.body( ).string( );
174 
175         JsonObject dataJson = new JsonObject( );
176         JsonElement rawJson = new JsonParser( ).parse( rawData );
177         if ( !rawJson.isJsonNull( ) )
178         {
179             dataJson = rawJson.getAsJsonObject( );
180         }
181 
182         AppLogService.info( "Received response :" );
183         AppLogService.info( rawData );
184 
185         switch ( response.code( ) )
186         {
187             case 400: // Wrong format
188                 throw new AuthorizationMalformedException( dataJson.get( AOTConstants.ERROR_MESSAGE ).getAsString( ) );
189             case 401: // Not authorized
190             case 403: // Forbidden
191                 throw new UnauthorizedAccessException( dataJson.get( AOTConstants.ERROR_MESSAGE ).getAsString( ) );
192             case 404: // Not found
193                 throw new AuthorizationNotFoundException( dataJson.get( AOTConstants.ERROR_MESSAGE ).getAsString( ) );
194             case 409: // Existing (conflict)
195                 throw new ExistingAuthorizationException( dataJson.get( AOTConstants.ERROR_MESSAGE ).getAsString( ) );
196             case 500: // Server error
197                 String message = dataJson.get( AOTConstants.ERROR_MESSAGE ).getAsString( );
198                 throw new Exception( message );
199             default: // Good request
200         }
201 
202         return dataJson;
203     }
204 
205     private Authorization getAuthorizationFromJson( JsonObject dataJson ) throws Exception
206     {
207         return new JaxbJacksonObjectMapper( ).readValue( dataJson.toString( ), Authorization.class );
208     }
209 
210 }