How to stream an encrypted file? - java

I want to stream an encrypted file from the back-end to the front end using a jersey rest API. I searched on the internet for some clues. I found something that i thought could get the job done: https://github.com/google/ExoPlayer/issues/2467. There is an example on how to random access an cipherinputstream. I can stream the video, but i can't search through the video with the standard html5 videoplayer slider.
The problem is i don't know how to get the offset from the videoplayer where the video needs to continue playing.
Below is my endpoint. The StreamingCipherInputStream is the same as in the link above.
`#GET
#Produces("video/mp4")
#Path("stream/{id}")
public Response streamVideo(#PathParam("id") int id) throws Exception {
Video video = videoservice.getVideo(id);
StreamingCipherInputStream in =
videoservice.getVideoInputStream(video.getFilename());
StreamingOutput entity = output -> {
ReaderWriter.writeTo(in, output);
};
return Response.ok(entity).build();
}`
My question is how can i make it work with everything i have or are the some better options i'm missing?

Related

How to read Json from online instead of asset folder

I was learning to make quiz app from online and it is going well. I was wondering instead of reading json from assets , it will be wise to read from online such that question can be added or changes accordingly and user don't have to update app.
Here is the JSON Structure.
{"questions" : [{"category":"general","question": "Grand Central Terminal, Park Avenue, New York is the world's", "choices": ["largest railway station","highest railway station","longest railway station","None of the above"], "correctAnswer":0},
{"category":"science","question": "Entomology is the science that studies", "choices": ["Behavior of human beings","Insects","The origin and history of technical and scientific terms","the formation of rocks"], "correctAnswer":1},
{"category":"science", "question":"What is known as the 'master gland' of the human body?", "choices":["Thyroid gland","Pituitary gland","Pineal gland","Pancreas"],"correctAnswer":1}
]}
and the code to read from assets is
private String loadJSONFromAsset() {
String json = null;
try {
InputStream is = mContext.getAssets().open("questionsJSON.json");
int size = is.available();
byte[] buffer = new byte[size];
is.read(buffer);
is.close();
json = new String(buffer, "UTF-8");
} catch (IOException ex) {
ex.printStackTrace();
return null;
}
return json;
}
I would like to show progress loading dialog when next question loads and any help will be largely appreciated. Thanks in advance.
Best option will be using REST APIs, Get data from Server/Database, which can be edited anytime from anywhere
You can learn to use Node js, it is not hard and it is based on JavaScript.
For getting JSON from APIs you can use Retrofit
Learning and implementing these things will be a bit hard if you are beginner but it will be the best option for long run
hope this helped!
Maybe consider using two different threads (or Runnables), one thread for downloading the JSON content and the other thread for displaying the GUI. For example, take a look at this: Stackoverflow Post
The solution involved making a Runnable that would first start downloading the data from the online website and then update the current progress onto the GUI thread as it is downloading. He uses the BufferedInputStream class so he can use a while loop to read the data in, update the number of bytes downloaded, get the current progress, and then display the results. I suppose you can do something similar here by using a while loop, and then checking if the download is finished. If so, you can close the display.

Jersey Post request - How to perform a file upload with an unknown number of additional parameters?

I asked something like this previously, but upon re-reading my original post, it was not easy to understand what I was really asking. I have the following situation. We have (or at least I'm trying to get working) a custom file upload procedure that will take in the file, a set number of 'known' metadata values (and they will always be there), as well as potentially an unknown number of additional metadata values. The service that exists currently uses the Jersey framework (1.16)
I currently have both client and server code that handles dealing with the file upload portion and the known metadata values (server code below)
#POST
#Path("asset/{obfuscatedValue0}/")
#Consumes(MediaType.MULTIPART_FORM_DATA)
public UUID uploadBlob(#PathParam("obfuscatedValue0") Integer obfuscatedValue0,
#FormDataParam("obfuscatedValue1") String obfuscatedValue1,
#FormDataParam("obfuscatedValue2") String obfuscatedValue2,
#FormDataParam("obfuscatedValue3") String obfuscatedValue3,
#FormDataParam("obfuscatedValue4") String obfuscatedValue4,
#FormDataParam("obfuscatedValue5") String obfuscatedValue5,
#FormDataParam("file") InputStream uploadedInputStream) {
.....
}
...and excerpt of client code:
Builder requestBuilder = _storageService
.path("asset")
.path(obfuscatedValue0.toString())
.type(MediaType.MULTIPART_FORM_DATA)
.accept(MediaType.APPLICATION_JSON);
FormDataMultiPart part = new FormDataMultiPart()
.field("file", is, MediaType.TEXT_PLAIN_TYPE) // 'is' is an inputstream from earlier in code.
.field("obfuscatedValue1", obfuscatedValue1)
.field("obfuscatedValue2", obfuscatedValue2)
.field("obfuscatedValue3", obfuscatedValue3)
.field("obfuscatedValue4", obfuscatedValue4)
.field("obfuscatedValue5", obfuscatedValue5);
storedAsset = requestBuilder.post(UUID.class, part);
However, I need to pass a map of additional parameters that will have an unknown number of values/names. From what I've seen, there is no easy way to do this using the FormDataParam annotation like my previous example.
Based upon various internet searches related to Jersey file uploads, I've attempted to convert it to use MultivaluedMap with the content type set to "application/x-www-form-urlencoded" so it resembles this:
#POST
#Path("asset/{value}/")
#Consumes("application/x-www-form-urlencoded")
public UUID uploadBlob(#PathParam(value), MultivaluedMap<String,String> formParams) {
....
}
It's my understanding that MultivaluedMap is intended to obtain a general map of form parameters (and as such, cannot play nicely together in the same method bearing #FormDataParam annotations.) If I can pass all this information from the Client inside some sort of map, I think I can figure out how to handle parsing the map to grab and 'doMagic()' on the data to get what I want done; I don't think I'll have a problem there.
What I AM fairly confused about is how to format the request client-side code when using this second method within the jersey framework. Can anyone provide some guidance for the situation, or some suggestions on how to proceed? I'm considering trying the solution proposed here and developing a custom xml adapter to deal with this situation, and sending xml instead of multipart-form-data but I'm still confused how this would interact with the InputStream value that will need to be passed. It appears the examples with MultivaluedMap that I've seen only deal with String data.

Android/Java How to read this file on website?

www.rgrfm.be/rgrsite/maxradio/android.php
www.rgrfm.be/rgrsite/maxradio/onair.txt
The track information of the music being played is contained in onair.txt. android.php is a php script I wrote.
I need to display the track information in my Android application. I do not want do download it to disk but keep it in memory. I don't know if the php script is useless because it would create additional overhead. So it's probably better to simply parse onair.txt
InputStream is = new URL("http://www.rgrfm.be/rgrsite/maxradio/onair.txt").openStream();
I am stuck with this. Has anyone got time to help me?
As described, php script seems useless. Since, you can directly read the text file. So, first read it as text, then parse it.
URL url = new URL("http://www.rgrfm.be/rgrsite/maxradio/onair.txt");
String text = readAsText(url)
parse(text);
String readAsText(URL url) {
// read the url as text here.
}
void parse(String text) {
}

Upload image to server using POST

I know that there are some similar questions to this one on the site, and I've read most of them. I've also Googled for a solution, but am still having issues.
So, in my project I need to catch multipart post requests that are used to send mixed data (an image, two strings (company, type), date data (month, year) and a few integers) from a client. Upon receiving this request I need to change contrast and brightness of the image, and modify the color to gray tones.
For debugging I use Postman Chrome Extension, and for now I am only focusing on sending the image. I've tested sending the request in different ways, in half of them I get a "404 Not Found" error, in the other half wrong data is returned (mostly array of 0). Below is the code used in my resource method:
#Component
#Path("/code")
#Produces("application/json")
public class EncodeResource extends BasicResource {
#POST
#Path("/encode")
#Consumes("multipart/form-data")
public String encodeImage(
#FormDataParam("image") InputStream imageInputStream) {
BufferedImage imageBuffer = null;
try {
imageBuffer = ImageIO.read(imageInputStream);
} catch (IOException e) {
e.printStackTrace();
}
if (imageBuffer != null)
return okResponse(<some parameters>);
else
return errorResponse(<some parameters>);
}
}
ImageInputStream contains some byte array, but ImageIO.read() always returns null. I tried different images with different extensions (which imageio can read by default, checked it), but got the same result. As I think, it happens cause of there are some "unnecessary" information in my inputStream, so imageio.read() can't convert it into any type of image. I've suddenly found it, when changed InputStream to File:
#FormDataParam("image") File imageInputStream
...and then checked saved by tomcat .tmp file. It looked like that:
------WebKitFormBoundary4nC1XD4cevbbRh7A
Content-Disposition: form-data; name="image"; filename="1.jpg">
Content-Type: image/jpeg
(a lot of bytes)
------WebKitFormBoundary4nC1XD4cevbbRh7A--
And of course imageio.read() returned null.
Summing up all of that, I have 2 questions actually:
Why did I get 404 error and how can i fix it? For example, I tried this and like here. And I had to delete the second #FormDataParam from here to receive at least something. Can it be cause of the Postman "specific" form-data requests?
Why did I get the wrong data? Maybe I can parse received file and get "correct" byte array? Or something else?..

Generating a PDF using a PUT operation

I have a web application that can display a generated PDF file to the user using the following Java code on the server:
#Path("MyDocument.pdf/")
#GET
#Produces({"application/pdf"})
public StreamingOutput getPDF() throws Exception {
return new StreamingOutput() {
public void write(OutputStream output) throws IOException, WebApplicationException {
try {
PdfGenerator generator = new PdfGenerator(getEntity());
generator.generatePDF(output);
} catch (Exception e) {
logger.error("Error getting PDF file.", e);
throw new WebApplicationException(e);
}
}
};
}
This code takes advantage of the fact that I only need so much data from the front end in order to generate the PDF, so it can easily be done using a GET function.
However, I now want to return a PDF in a more dynamic way, and need a bunch more information from the front end in order to generate the PDF. In other areas, I'm sending similar amounts of data and persisting it to the data store using a PUT and #FormParams, such as:
#PUT
#Consumes({"application/x-www-form-urlencoded"})
public void put(#FormParam("name") String name,
#FormParam("details") String details,
#FormParam("moreDetails") String moreDetails...
So, because of the amount of data I need to pass from the front end, I can't use a GET function with just query parameters.
I'm using Dojo on the front-end, and all of the dojo interactions really don't know what to do with a PDF returned from a PUT operation.
I'd like to not have to do this in two steps (persist the data sent in the put, and then request the PDF) simply because the PDF is more "transient" in this uses case, and I don't want the data taking up space in my data store.
Is there a way to do this, or am I thinking about things all wrong?
Thanks.
I can't quite understand what do you need to accomplish - looks like you want to submit some data to persist it and then return pdf as a result? This should be straightforward, doesn't need to be 2 steps, just submit, on the submit save the data and return PDF.
Is this your problem? Can you clarify?
P.S.
Ok, you need to do the following in your servlet:
response.setHeader("Content-disposition",
"attachment; filename=" +
"Example.pdf" );
response.setContentType( "application/pdf" );
Set the "content-length" on the response, otherwise the Acrobat Reader plugin may not work properly, ex. response.setContentLength(bos.size());
If you provide output in JSP you can do this:
<%# page contentType="application/pdf" %>

Categories