How to return an image file (Byte[]) as a compressed file with Spring API? - spring

I'm the company's file server
Get the file as byte[] through the image path and authentication key.
(This server is not accessible to me.)
What I want to do is, when the user downloads the selected files, I want to compress these files and provide them as a compressed file.
Since the company's file server does not have a download API for multiple files, I think I need to request as many APIs as the number of file lists with a for statement in my service API.
In other words, it seems that we need to take a List<Byte[]> and compress this list.
Is there something wrong with my method?
And can I pass the result as json after compression? (I confirmed that the image file is passed as json.)

Related

Uploading unique files at concurrent load using JMeter

We have usecase where we need to call an API that uploads its respective category of unique file.
For every API call we need to use a unique FileName. I mean File once used in an API call should not be used again.
For Example
CarAPI will be called by uploading a file-name from list of files (CarAP_1.xml to CarAP_1000.xml files)
File CarAP_1.xml once used in an API call should not be used again in next call
BikeAPI will be called by uploading a file-name from list of files (BikeAP_1.xml to BikeAP_1000.xml files)
File once used in an API call should not be used again.
Any thoughts or inputs on how we can achieve this using JMeter.
You can put these filenames
either to a CSV file and use HTTP Simple Table Server, its READ endpoint has KEEP=false mode so once the data is used it will be removed from memory hence you can avoid duplicate requests
or to Redis and use Redis Data Set Config which also provides possibility to remove the data from the list once it has been utilized
Both plugins can be installed using JMeter Plugins Manager

Can I serve files stored in Google Cloud Storage via a http.FileServer in golang?

I have developed a small web application that runs a web server in golang.
Each user can login, view the list of their docs (previously uploaded) and click on an item to view an html page that shows some fields of the document plus an tag with a src attribute
The src attribute includes an url like "mydocuments/download/123-456-789.pdf"
On the server side I handle the URL ("mydocuments/download/*") via an http Handler
mymux.HandleFunc(pat.Get("/mydocuments/download/:docname"), DocDownloadHandler)
where:
I check that the user has the rights to view the document in the url
Then I create a fileserver that obviously re-maps the url to the real path of the folder where the files are stored on the filesystem of the server
fileServer := http.StripPrefix("/mydocs/download/",http.FileServer(http.Dir("/the-real-path-to-documents-folder/user-specific-folder/)))
and of course I serve the files
fileServer.ServeHTTP(w, r)
IMPORTANT: the directory where the documents are stored is not the static-files directory I sue for the website but a directory where all files end after being uploaded by users.
My QUESTION
As I am trying to convert the code for it to work also on Google Cloud, I am trying to change the code so that files are stored in a bucket (or, better in "sub-directories" -as they do not properly exist- of a bucket).
How can I modify the code so to map the real document url as available via the cloud storage bucket?
Can I still use the http.FileServer technique above (if so what should I use instead of http.Dir to map the bucket "sub-folder" path where the documents are stored)?
I hope I was enough clear to explain my issue...
I apologise in advance for any unclear point...
Some options are:
Give the user direct access to the resource using a signed URL.
Write code to proxy the request to GCS.
Use http.FS with an fs.FS backed by GCS.
It's possible that a fs.FS for GCS already exists, but you may need to write one.
You can use http.FileSystem since it is an interface and can be implemented however you like.

Uploading images to Spring Boot and S3 all In-Memory

I have an Angular webapp that uses a Spring Boot REST service as its backing web service.
I am adding a "Profiles" feature for users, and as part of this I want to stand up an endpoint that allows users to upload profile images for themselves and immediately upload those files to S3 (where I will host all the images from).
Looking at several Spring Boot/file upload tutorials :
http://www.mkyong.com/spring-boot/spring-boot-file-upload-example/
I update avatar image and display it but the avatar does not change in Spring Boot , why?
Many others
It seems that the standard way of handling such file upload is exposing a controller endpoint that accepts MultipartFiles like so:
#RestController
#RequestMapping("/v1/profiles")
public class ProfileController {
#PostMapping("/photo")
public ResponseEntity uploadProfilePhoto(#RequestParam("mpf") MultipartFile mpf)
// ...
}
Looking at all this code, I can't tell if the MultipartFile instance is in-memory or if Spring sets its location somewhere (perhaps under /tmp?) on the disk.
Looking at the AWS S3 Java SDK tutorial, it seems the standard way to upload a disk-based File is like so:
File file = new File(uploadFileName);
s3client.putObject(new PutObjectRequest(bucketName, keyName, file));
So it looks like I must have a File on disk in order to upload to S3.
I'm wondering if there is a way to keep everything in memory, or whether this is a bad idea and I should stick to disks/File instances!
Is there a way to keep the entire profile image (MultipartFile) in-mempory inside the controller method?
Is there a way to feed (maybe via serialization?!) a MultipartFile instance to S3's PutObjectRequest?
Or is this all a terrible idea (if so, why?!)?
Is there a way to keep the entire profile image (MultipartFile) in-mempory inside the controller method?
No, there is NO way to keep an image File in-memory because File object in java represents a path in file system.
Is there a way to feed (maybe via serialization?!) a MultipartFile instance to S3's PutObjectRequest?
No, from S3's API documentation, there is no way for S3 to deserialize to the image file for you after/during the upload.
Or is this all a terrible idea (if so, why?!)?
It depends on your specific case but it is generally not preferred.
If - there are not many users uploading images at the same time, your memory is probably enough to handle.
Else - You can easily get out-of-memory problems.
If you insist on doing so, S3 API can upload an InputStream (If I remember correctly). You can convert your Multipart File to an InputStream.
This SO thread talks about uploading to S3 with InputStream
You can also take a look at File.createTempFile() to create a temp file.
I have been looking at the same thing. Basically you want a user to be able to be able to upload a photo album and have those photos served from S3 and probably have them secured so only that user can upload/delete/etc.
I believe the simpler answer is in spring boot to get a Pre-signed URL from S3. https://docs.aws.amazon.com/AmazonS3/latest/dev/PresignedUrlUploadObjectJavaSDK.html
which basically gives you a token defining the bucket, and object key ("/bobs_profile/smiling_bob.jpg") and a time limit for that image to be uploaded.
Give that to your angular app (or ionic app) to upload the image to that location.
That should do it. but someone let me know if I'm wrong.
The only issue that I see is if bob wants to upload "bobs_nude_photo.jpg" and only wants spring security logged in people to be able to see it... well I'm sure there is an S3 solution for that??

How to decode and inspect an HTTP payload when it is a zip

So I'm pretty new at all this. I am trying to reverse engineer a web application.
When I submit a form, it sends a POST with a request payload that looks something similar to this:
encoding=UTF8&zip=1&size=136240&html=DwQgIg_a_whole_lot_more_gibberish_not_worth_posting
Anyways, from inspecting the captured traffic from Chrome developer tools, I noticed it is encoded and sent as a zipped up html?
How would I go about reversing this to see what the content is actually being sent to the server?
What you want to do is this:
1) Get the name of the zip file
2) Get the path of the zip file (likely the root directory or the current path the form is at)
3) Generate the URL (http://site_name.com/path/to/folder/zip_file.zip)
4) Download it using a too such as wget (typing the URL into the browser may work too)
I used this technique to download all the files that get downloaded to the OTA updates on iOS devices (used burp suit to intercept the zip file name where the server was on my computer which my iDevice was connected to).
Please note: the name of the zip file you have given does not end in .zip. this may mean it doesn't have a extension; you may have to add .zip to the file manually; or it may have another ending such as .tar, .tar.gz etc.

Codenameone getting the byte[] of a file

After this line:
String photoFileLocation = Capture.capturePhoto();
I want to transmit such image to a server. How Can I get the bytes[] of the file which name is in the variable 'photoFileLocation'?
Use FileSystemStorage to open files.
But for actual file upload you should use MultipartRequest which accepts file URL's (more efficient than reading bytes). You can see an example of this including the server code in the recent workshop we released https://www.codenameone.com/blog/build-mobile-ios-apps-in-java-using-codename-one-on-youtube.html
You can see a full sample in the JavaDoc for multipart request here: https://www.codenameone.com/javadoc/com/codename1/io/MultipartRequest.html

Resources