How To Upload Single and Multiple Files in Golang 2024
How To Upload Single and Multiple Files in Golang 2024
Home Categories
This article will teach you how to upload single and multiple files on a
Golang web server. The tutorial focuses on image upload, but the concepts
can be extended and used for any file type.
···
Now Playing
When building APIs for either Web, Mobile, or Desktop apps, very often, the
need to make provision for file upload arises. Therefore, knowing how to
upload and process files in Golang will give you more confidence when
At the end of this comprehensive guide, you should know how to:
Upload and resize multiple images before storing them on the disk
More practice:
Prerequisites
···
Have the latest version of Golang installed on your system
3. Open the integrated terminal in your IDE and run go mod tidy to
4. Start the Gin Gonic HTTP server with go run main.go or use the
https://github.com/cosmtrek/air library if you need the hot-reloading
feature.
To get started, navigate to the location you would like to set up the project
Now that you’ve created the project module, install the Gin Gonic package
with this command. Gin Gonic is an HTTP web framework written in Go.
1 go get -u github.com/gin-gonic/gin
Next, create a main.go file and add the following code snippets:
main.go
1 package main
2
3 import (
4 "github.com/gin-gonic/gin"
5 )
6
7 func main() {
8 router := gin.Default()
9
10 router.GET("/healthchecker", func(ctx *gin.Context) {
11 ctx.JSON(200, gin.H{"status": "success", "message": "How to Upload Sing
12 })
13
14 router.Run(":8000")
15 }
16
The above code will create a Gin Gonic engine instance, add a health
checker route to the middleware pipeline and start the HTTP server on port
Congrats if you have made it this far. We will continue by creating the file
upload components with HTML, CSS, and JavaScript. After that, we will use
Gin Gonic to parse and render the HTML markup.
Step 2 – Create the File Upload Components
Below is a preview of the file upload components. The HTML markup will
OFERTAS DO CONSUMIDOR
OS DESCONTOS
CHEGARAM
Ver Ofertas
Beyond Fast
HowtoSetup tRPCCRUD TS
Golang
Forget/Reset
SQLC Reset
Golang
Password
API NEXT.
Password
JWT GOFileUpload
Authentication
CRUD TS
SingleFileUpload
ChooseFileNofilechosen
MultipleFileUpload
ChooseFiles7files
templates/index.html
90 imgHolder.appendChild(imgElement);
91 IMAGE_PREVIEW.appendChild(imgHolder);
92 } catch (error) {
93 alert(error.message);
94 }
95 });
96
97 // Mulitple File Upload
98 document
99 .getElementById("mulitple_files_upload")
100 .addEventListener("change", async (event) => {
101 try {
102 let formData = new FormData();
103 for (let key in event.target.files) {
104 formData.append("images", event.target.files[key]);
105 }
106 const data = await fetch(`${SERVER_ENDPOINT}/upload/multiple
107 body: formData,
108 method: "POST",
109 }).then((res) => res.json());
110
111 data.filepaths.forEach((filepath) => {
112 const imgHolder = document.createElement("div");
113 const imgElement = document.createElement("img");
114 imgHolder.classList.add("file-preview__el");
115 imgElement.classList.add("file-preview__img");
116 imgElement.src = filepath;
117 imgHolder.appendChild(imgElement);
118 IMAGE_PREVIEW.appendChild(imgHolder);
119 });
120 } catch (error) {
121 alert(error.message);
122
123 }
124 });
125 </script>
126 </body>
</html>
Then, we wrote some logic to upload single and multiple files with
JavaScript.
Now that we have the HTML template, let’s write some code to render
index.html on the root route. Open main.go file and replace its content
main.go
1 package main
2
3 import (
4 "net/http"
5
6 "github.com/gin-gonic/gin"
7 )
8
9 func main() {
10 router := gin.Default()
11
12 router.LoadHTMLGlob("templates/*")
13 router.GET("/healthchecker", func(ctx *gin.Context) {
14 ctx.JSON(200, gin.H{"status": "success", "message": "How to Upload Sing
15 })
16
17 router.GET("/", func(ctx *gin.Context) {
18 ctx.HTML(http.StatusOK, "index.html", nil)
19 })
20 router.Run(":8000")
21 }
22
After that, start the Gin HTTP server with go run main.go and open
Let’s go ahead and write the code required for uploading and processing
the files.
In this section, you will create a route function to retrieve the uploaded file
and store it in the filesystem. Handling file upload in Golang can be a little
To handle
a single file, we will use Gin’s .FromFile() method that’s
available on the context object to retrieve the uploaded file from the multi-
part content.
main.go
1 func uploadSingleFile(ctx *gin.Context) {
2
file, header, err := ctx.Request.FormFile("image")
3 if err != nil {
4
ctx.String(http.StatusBadRequest, fmt.Sprintf("file err : %s"
5 return
6 }
7
8 fileExt := filepath.Ext(header.Filename)
9 originalFileName := strings.TrimSuffix(filepath.Base(header.Filename
10 now := time.Now()
11 filename := strings.ReplaceAll(strings.ToLower(originalFileName
12 filePath := "http://localhost:8000/images/single/" + filename
13
14 out, err := os.Create("public/single/" + filename)
15 if err != nil {
16 log.Fatal(err)
17 }
18 defer out.Close()
19 _, err = io.Copy(out, file)
20 if err != nil {
21 log.Fatal(err)
22 }
23 ctx.JSON(http.StatusOK, gin.H{"filepath": filePath})
24 }
Let’s evaluate the above code. First, we attempt to retrieve the file with the
name “image” from the multi-part content and check if the file is received
successfully. To avoid conflicts with the file names, we appended a Unix
time to the original file name, called the os.Create() method to create
the file in the public/single/ directory, and used an if statement to
10 % CÓDIGO: LATAMBR10
After that, we called the io.Copy() method to copy the uploaded file to
incríveis
#StaySafewithMelia
the file system at the specified destination. If everything goes well, and the
file was stored on the disk, we will return the file path to the client.
Now let’s handle the case where we want to process the uploaded file
before storing it in the file system. Since we are dealing with images, we will
use the https://github.com/disintegration/imaging package to process
···
1 go get -u github.com/disintegration/imaging
After that, we will call the image.Decode() method to decode the file from
···
Once the image has been resized and there is no error, we will call the
···
main.go
Now let’s handle the case where the client uploads multiple files to the
server. To do that, we will create a route function that will extract the files
from the multipart content, modify the origin filenames, and save the files
to the filesystem. We can manually parse and iterate over each file but Gin
···
main.go
method and stored the result in a form variable. Then, we extracted the
multipart content with the name images from form.File[] , looped
through the list of files, modified the filenames, and stored the files on the
disk.
···
If everything goes well and the files were stored in the filesystem, a slice
holding the file paths will be returned to the client.
···
···
time we will resize the images before storing them in the filesystem. After
looping through the multipart files, Imaging‘s image.Decode() method will
be called to decode the images from multipart.File to image.Image .
···
main.go
···
Now let’s create routes to evoke the route handlers. The API will have four
routes:
Because the files are to be stored on the disk, we need to create folders that
represent the folder structure we passed to the os.Create() and
create the folders if they don’t exists before the main function gets called.
main.go
1 package main
2
3 import (
4 "errors"
5 "fmt"
6 "image"
7 "io"
8 "log"
9 "net/http"
10 "os"
11 "path/filepath"
12 "strings"
13 "time"
14
15 "github.com/gin-gonic/gin"
16
17 "github.com/disintegration/imaging"
18 )
19
20 func uploadResizeSingleFile(ctx *gin.Context) {
21 file, header, err := ctx.Request.FormFile("image")
22 if err != nil {
23 ctx.String(http.StatusBadRequest, fmt.Sprintf("file err : %s"
24 return
25 }
26
27 fileExt := filepath.Ext(header.Filename)
28 originalFileName := strings.TrimSuffix(filepath.Base(header.Filename
29 now := time.Now()
30 filename := strings.ReplaceAll(strings.ToLower(originalFileName
31 filePath := "http://localhost:8000/images/single/" + filename
32
33 imageFile, _, err := image.Decode(file)
34 if err != nil {
35 log.Fatal(err)
36 }
37 src := imaging.Resize(imageFile, 1000, 0, imaging.Lanczos)
After implementing all the above code, start the Gin HTTP server by running
go run main.go .
···
Conclusion
Congrats! You have made it to the end, and I hope you’ve learned how to
upload and process files in Golang. Take it up as a challenge, add more
Share Article:
https://codevoweb.com/how-to-upload-single-and-multiple-files-in-golang/
Tags: Golang Golang API
May 4, 2023
Leave a Reply
Comment
Name Email
Save my name, email, and website in this browser for the next time I comment.
This site is protected by reCAPTCHA and the Google Privacy Policy and Terms of
Service apply.
Post Comment
This site uses Akismet to reduce spam. Learn how your comment data is processed.
Support Me!
···
Recent posts
February 10, 2024
February 7, 2024
February 7, 2024
February 5, 2024
Categories
C# (2)
C++ (1)
Deno (8)
Golang (28)
JavaScript (4)
NextJs (36)
NodeJS (32)
Programming (19)
Python (17)
React (35)
Rust (31)
Svelte (5)
Vue (7)
···
Tag Cloud
React Hook Form ReactJs React Query RTK Query Rust Svelte
···