1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34 package fr.paris.lutece.plugins.filegenerator.service;
35
36 import java.io.File;
37 import java.io.IOException;
38 import java.nio.file.DirectoryStream;
39 import java.nio.file.Files;
40 import java.nio.file.Path;
41 import java.nio.file.Paths;
42 import java.util.ArrayList;
43 import java.util.List;
44 import java.util.Locale;
45 import java.util.concurrent.CompletableFuture;
46
47 import fr.paris.lutece.plugins.filegenerator.business.TemporaryFile;
48 import fr.paris.lutece.plugins.filegenerator.business.TemporaryFileHome;
49 import fr.paris.lutece.portal.business.physicalfile.PhysicalFile;
50 import fr.paris.lutece.portal.business.user.AdminUser;
51 import fr.paris.lutece.portal.service.i18n.I18nService;
52 import fr.paris.lutece.portal.service.util.AppLogService;
53 import fr.paris.lutece.portal.service.util.AppPropertiesService;
54 import fr.paris.lutece.util.file.FileUtil;
55
56
57
58
59 public class TemporaryFileGeneratorService
60 {
61 private static final TemporaryFileGeneratorServiceemporaryFileGeneratorService.html#TemporaryFileGeneratorService">TemporaryFileGeneratorService INSTANCE = new TemporaryFileGeneratorService( );
62 private static final Integer FILE_MAX_SIZE = Integer.parseInt( AppPropertiesService.getProperty( "temporaryfiles.max.size", "0" ) );
63 private static final String KEY_FILE_TOO_BIG = "filegenerator.temporaryfile.file.too.big";
64 private static final Object LOCK = new Object( );
65
66 public static TemporaryFileGeneratorService getInstance( )
67 {
68 return INSTANCE;
69 }
70
71 public void generateFile( IFileGenerator generator, AdminUser user )
72 {
73 CompletableFuture.runAsync( new GenerateFileRunnable( generator, user ) );
74 }
75
76 private static final class GenerateFileRunnable implements Runnable
77 {
78
79 private IFileGenerator _generator;
80 private AdminUser _user;
81
82
83
84
85
86
87
88 public GenerateFileRunnable( IFileGenerator generator, AdminUser user )
89 {
90 _generator = generator;
91 _user = user;
92 }
93
94 @Override
95 public void run( )
96 {
97 int idFile = TemporaryFileService.getInstance( ).initTemporaryFile( _user, _generator.getDescription( ) );
98 synchronized( LOCK )
99 {
100 Path generatedFile = null;
101 try
102 {
103 generatedFile = _generator.generateFile( );
104 }
105 catch( IOException e )
106 {
107 AppLogService.error( "Error generating temporary file with id " + idFile, e );
108 }
109 updateTemporaryFile( generatedFile, idFile );
110 }
111 }
112
113 private void updateTemporaryFile( Path generatedFile, int idFile )
114 {
115 TemporaryFile file = TemporaryFileHome.findByPrimaryKey( idFile );
116 if ( generatedFile != null )
117 {
118 try
119 {
120 PhysicalFile physicalFile = createPhysicalFile( generatedFile );
121 int size = physicalFile.getValue( ).length;
122 file.setSize( size );
123 if ( FILE_MAX_SIZE > 0 && size > FILE_MAX_SIZE )
124 {
125 file.setTitle( I18nService.getLocalizedString( KEY_FILE_TOO_BIG, Locale.getDefault( ) ) );
126 AppLogService.error( "File too big ( " + size + ") : Max size is " + FILE_MAX_SIZE );
127 }
128 else
129 {
130 file.setTitle( _generator.getFileName( ) );
131 file.setMimeType( _generator.getMimeType( ) );
132 file.setDescription( _generator.getDescription( ) );
133 String physicaId = TemporaryFileService.getInstance( ).savePhysicalFile( file, physicalFile );
134 file.setIdPhysicalFile( physicaId );
135 }
136 }
137 catch( IOException e )
138 {
139 AppLogService.error( "Error storing temporary file with id " + idFile );
140 file.setTitle( "" );
141 file.setSize( -1 );
142 }
143 finally
144 {
145 if ( generatedFile.toFile( ).isDirectory( ) )
146 {
147 for ( File fileToDelete : generatedFile.toFile( ).listFiles( ) )
148 {
149 FileUtil.deleteFile( fileToDelete );
150 }
151 }
152 FileUtil.deleteFile( generatedFile.toFile( ) );
153 }
154 }
155 else
156 {
157 file.setSize( -1 );
158 }
159
160 TemporaryFileHome.update( file );
161 }
162
163 private PhysicalFile createPhysicalFile( Path generatedFile ) throws IOException
164 {
165 PhysicalFile physicalFile = new PhysicalFile( );
166 if ( _generator.hasMultipleFiles( ) )
167 {
168 List<Path> files = new ArrayList<>( );
169 try ( DirectoryStream<Path> stream = Files.newDirectoryStream( generatedFile ) )
170 {
171 for ( Path path : stream )
172 {
173 files.add( path );
174 }
175 }
176 createZipPhysicalFile( generatedFile, physicalFile, files.toArray( new Path [ files.size( )] ) );
177 }
178 else
179 if ( _generator.isZippable( ) )
180 {
181 createZipPhysicalFile( generatedFile, physicalFile, generatedFile );
182 }
183 else
184 {
185 physicalFile.setValue( Files.readAllBytes( generatedFile ) );
186 }
187 return physicalFile;
188 }
189
190 private void createZipPhysicalFile( Path generatedFile, PhysicalFile physicalFile, Path... filesToZip ) throws IOException
191 {
192 Path zipFile = Paths.get( generatedFile.getParent( ).toString( ), _generator.getFileName( ) );
193 try
194 {
195 FileUtil.zipFiles( zipFile, filesToZip );
196 physicalFile.setValue( Files.readAllBytes( zipFile ) );
197 }
198 finally
199 {
200 FileUtil.deleteFile( zipFile.toFile( ) );
201 }
202 }
203 }
204
205 }