3

We have a content management system to allow our users to store files uploaded through a REST web service. Before storing these files in the repository, their contents are encrypted.

When retrieving these files, the file contents are decrypted, and placed into a byte array. The intention is to pass these contents back to the client as a file attachment that they can store on their local machines.

To do this, I'm currently storing the contents into a temp file and passing the temp file back as the attachment. This approach had the nasty side effect of the previously encrypted repository file, being stored "in the clear" in the temporary directory.

I know I can set the temp file to auto delete when the JVM ends, but since this is a server, there may be a long time between server restarts.

I can also (I guess) set up some sort of listener job to check the temp directory periodically and delete files past a certain age, but that seems cumbersome and doesn't really solve the issue - it just shortens the exposure time.

I'm looking for alternatives to avoid the temporary file, but still allow the user to download the (preferably in memory) file as an attachment via a web service.

Any idea?

Thanks!

Vinnie
  • 12,400
  • 15
  • 59
  • 80
  • 2
    Do not use deleteOnExit - it is useful only for developing. It leaks the file name until the entire JVM is stopped. – bestsss Jun 16 '11 at 15:34

5 Answers5

2

Are Streams an option? Drawback is that you store everything in memory.

Miki
  • 7,052
  • 2
  • 29
  • 39
  • This is kind of what I was hoping to do, but didn't know how to steam the result back through the Http Response. Is that possible? FWIW I'm using Restlet as my REST WS framework. – Vinnie Jun 16 '11 at 15:39
2

Well I guess you could store the data in a Java Object e.g. HashMap and use that as the cache (use weak references so the cache can get garbage collected if the Garbage Collector decides to do this). If this means dire consequences for the amount of heap in use then you could look at running memcache or a Java equivalent e.g. ehcache to store your Objects away from the JVM heap.

Is there a reason you can't just stream the result back, so that when it's finished it gets cleaned up by the JVM?

planetjones
  • 12,469
  • 5
  • 50
  • 51
  • This is kind of what I was hoping to do (use streams), but didn't know how to steam the result back through the Http Response. Is that possible? FWIW I'm using Restlet as my REST WS framework. – Vinnie Jun 16 '11 at 15:41
  • I think you'd just get the HTTP response.getOutputStream(); write to it and then flush it. – planetjones Jun 16 '11 at 15:44
  • It is as simple as streaming the bytes to the HttpServletRepose output stream? Maybe I over thought this... thanks – Vinnie Jun 16 '11 at 15:46
  • yeah you just want a FileInputStream to read your file, then write that stream into the OutputStream of the HTTP Response. Let us know how you get on. – planetjones Jun 16 '11 at 15:51
1

Is there any reason why you have to pass a File object back, or is this something that you could change?

The reason I ask is, you could create an interface which had a few methods such as getName(), getContentStream() etc, and then pass that back instead of a concrete File object.

0

One thing you could look into instead of a file is Memcached and delete the file once you are done decrypting it.

Also, you could just store the encrypted file in a db as a blob and retrieve it as a stream. Then you should be able to decrypt it on the fly.

John Kane
  • 4,383
  • 1
  • 24
  • 42
0

could you not just keep a reference to the clear temp file and delete it as soon as the encryption is done? Perhaps describe more of your processes surrounding this as what is doing the file creation ?

iowatiger08
  • 1,892
  • 24
  • 30