Creating a basic HTTP server with Go

3 min read

Published at December 7, 2023 by ahsanzizan

Go (or Golang) is a powerful and efficient programming language that excels in building scalable and concurrent applications. In this occasion, we'll walk through the process of creating a simple HTTP server using Go. By the end of this guide, you'll have a basic understanding of how to handle HTTP requests and responses. Today, I'm going to share what I've learnt so far about building an HTTP server wiht Go.

Prerequisites

Before we begin, make sure you have Go installed on your machine. You can download it from the official Go website.

Project Setup

mkdir go-http-server
cd go-http-server

Now, create a file named main.go for our Go code.

// main.go

package main

import (
	"fmt"
	"net/http"
)

func main() {
	// Your HTTP server code will go here
}

Handling an HTTP Request

To handle HTTP requests, we'll use the http package provided by Go. Let's create a simple HTTP handler function that responds to incoming requests.

import (
	"errors"
	"fmt"
	"io"
	"net/http"
	"os"
)

func get(w http.ResponseWriter, r *http.Request) {
	fmt.Printf("Responding to GET / /\n")
	io.WriteString(w, "Hello World!\n")
}

Now, let's register this handler function in our HTTP server

func main() {
	http.HandleFunc("/", get)

	err := http.ListenAndServe(":8080", nil)
    if errors.Is(err, http.ErrServerClosed) {
		fmt.Printf("Server closed\n")
	} else if err != nil {
		fmt.Printf("Error starting server: %s\n", err)
		os.Exit(1)
	}
}

Run Your HTTP Server

Save the changes applied to main.go, and you can now run your HTTP server.

go run main.go

Visit http://localhost:8080 in your web browser, and you should see the message "Hello World!".

You can also use the curl command in cmd and you'll also get the same response

curl http://localhost:8080/

And that's it! You have your first HTTP server built with Go.

You can expand it a bit further by using mux to multiplex a server and http.Handler implementation by net/http package, which you can use for a case like this.

package main

import (
	"encoding/json"
	"errors"
	"fmt"
	"math/rand"
	"net/http"
	"os"
)

type User struct {
	ID   string `json:"id"`
	Name string `json:"name"`
}

var users map[string]User
var letterRunes = []rune("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ")

func generateId(n int) string {
	b := make([]rune, n)
	for i := range b {
		b[i] = letterRunes[rand.Intn(len(letterRunes))]
	}

	return string(b)
}

func getUsers(w http.ResponseWriter, r *http.Request) {
	fmt.Printf("Responding to GET /\n")

	usersList := make([]User, 0, len(users))

	for _, user := range users {
		usersList = append(usersList, user)
	}

	res, err := json.Marshal(usersList)
	if err != nil {
		http.Error(w, "Internal Server Error", http.StatusInternalServerError)
		return
	}

	w.Header().Set("Content-Type", "application/json")
	w.WriteHeader(http.StatusOK)
	w.Write(res)
}

func createUser(w http.ResponseWriter, r *http.Request) {
	fmt.Printf("Responding to POST /")

	var newUser User
	decoder := json.NewDecoder(r.Body)
	err := decoder.Decode(&newUser)

	if err != nil {
		http.Error(w, "Bad Request", http.StatusBadRequest)
		return
	}

	newUser.ID = generateId(12)
	users[newUser.ID] = newUser

	res, err := json.Marshal(newUser)
	if err != nil {
		http.Error(w, "Internal Server Error", http.StatusInternalServerError)
		return
	}

	w.Header().Set("Content-Type", "application/json")
	w.WriteHeader(http.StatusOK)
	w.Write(res)
}

func main() {
	users = make(map[string]User)

	mux := http.NewServeMux()
	mux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
		switch r.Method {
		case http.MethodGet:
			getUsers(w, r)
		case http.MethodPost:
			createUser(w, r)
		}
	})

	err := http.ListenAndServe(":8080", mux)

	if errors.Is(err, http.ErrServerClosed) {
		fmt.Printf("Server closed")
	} else if err != nil {
		fmt.Printf("Error starting server: %s\n", err)
		os.Exit(1)
	}
}

Latest From Me

Whatever this is

*"Hold fast to dreams, for if dreams die, life is a broken-winged bird that cannot fly."* ## Bucketlist Bonsais' Bucketlist, because its never too late to explore the world. 1. Switzerland's villages 2. Japan's Countryside 3. West America (Cowboy and other cool stuff) 4. Northern Lights in Iceland or Norway 5. Pyramids of Giza in Egypt 6. Hot Air Balloon Ride Over Cappadocia, Turkey

Eleventh Grade in Review

Damn, what a year. Looking back at 11th grade, it's hard to believe all that happened and how much I accomplished. From the start, I knew it was going to be tough, but I had no idea how much I would learn and grow. The first day of school in July was nerve-wracking as usual. New classes, new teachers, new faces. I was super excited to dive into Mobile App Development but also a bit terrified. Pak Ilham turned out to be an amazing and chill teacher, though. He made even the most complex topics seem understandable. I also started participating in competitions this time around. By October, I had found my rhythm. I was ACING those Software Engineering classes. I spent countless hours practicing, learning new things in my room, and helping others through the tough spots. I even made it to the final stage of a web design competition—my first final experience. I was so damn nervous, but in the end, me and Gilang (shout out to my bro) managed to build several frontend projects, even though we didn’t win anything (🥲). I also finished my first Bromo trip with some friends. The end of October was challenging because I encountered a personal issue I'd never faced before, but I still managed to get over it and continue my 11th-grade journey. December brought a festive atmosphere to school. The Dies Natalis concert was a highlight—they invited Hal, an Indonesian singer, and other artists too. Finals were stressful because the exams didn’t go as expected, but I got through them with decent grades. The holiday break was perfect for recharging and spending time with family. Oh, January. The new year meant new resolutions. I promised myself to stay more organized and manage my time better. Easier said than done, right? But I did make some progress. I started using a planner religiously, which actually helped a lot. I started training for LKS too. February and March were incredibly busy. Between schoolwork, freelance projects, and preparing for LKS, I barely had time to breathe. My weekends were packed with study sessions and literally just coding. It was exhausting, but I knew it would all be worth it in the end. And here it is, February 24th, the LKS D-Day. It all went well until the final round when the judges asked me and Adit to prove my solution to the given problems in 5 minutes, and I completely panicked (since I’d never practiced for such situations). But thankfully, I won 1st place in the city-level LKS and got the opportunity to represent Malang in the prestigious LKS Jawa Timur in the field of AI. Between the end of March and the middle of April was LKS Jawa Timur. I came prepared and was kinda confident I’d bring home the trophy. But things went wrong on Day 1—our work wasn’t in the top 3 at all. Thankfully, Day 2 saved us (shoutout to Adit), and we managed to bag the trophy. May was the time to go back to school and leave my LKS training behind (since there’s no national-level for the AI field). But things started to wind down. The finals were not that hard, and I even found some time to hang out with friends and enjoy my time. June was a mix of emotions. On one hand, I was relieved that the school year was over. On the other hand, it was hard saying goodbye to my Sotel classmates. We went on a trip to a villa in Batu and enjoyed our time there. Looking back, 11th grade was a rollercoaster. There were highs and lows, but through it all, I learned a lot about myself. I became more resilient, found new passions, and strengthened my friendships. Now, I’m ready for the challenges and adventures that senior year will bring! (jk I'm scared as heck) ### ! Important **My Book of the Year**: The Living Room by Nicci French. <br> **Wishlist**: Tomorrow, and Tomorrow, and Tomorrow, Dell XPS-15. <br> **Song of the Year**: You Let Her Go Again by Reality Club

2024 So Far...

## New Chapter is Here! Hey there! I'm diving back into the world of blogging, though my updates might be as rare as a blue moon. How's life treating you? Hopefully, it's been as kind to you as it has to me this past year. Bagged the prestigious LKS AI (both at the province and city levels), snagged a slick new pair of kicks—still eyeing that shiny new laptop, though. Crossing my fingers for my 11th-grade report card; fingers crossed it matches my expectations. ![Photo of me winning the LKS AI Provinsi Jawa Timur](https://media.licdn.com/dms/image/D562DAQEaZLP3GgACbQ/profile-treasury-image-shrink_1280_1280/0/1714184882144?e=1718287200&v=beta&t=OuOv4YIf0al_dTeZFh2wGbJL8EMkTcY3nzl7jtgdF04) Been neck-deep in new projects lately, like revamping the OSIS Moklet Web-app to encompass all school organizations, not just the student council (also renaming it to Moklet.org). Also, whipped up the official website for LKBB Antareja, alongside a handful of freelance gigs. Oh, and I'm also competing in some competitions—Samsung Solve For Tomorrow (SSFT), a Web Programming showdown, with more on the horizon. Plus, I'm packing my bags, trading Banten for the greener pastures of West Java. But amidst all these events, I'm finding moments to breathe and appreciate the journey. Each project, each competition, each move feels like a step forward, a new chapter unfolding. And sure, it's a bit chaotic at times, juggling deadlines and dreams, but there's a thrill in the chaos, a sense of purpose driving it all forward.

2023: My Most Transformative Year

You know, like everybody else in this world, I've always planning some revolutionary things to do next year. But like everybody else in this world, I've never really done any revolutionary things in each year so..... ![Foto LKS](https://drive.google.com/uc?export=view&id=1p4_ZdBav70drrMT2QMIqgNk33Ua3i8NR) As we bid farewell to 2023 and step into the unknown corridors of 2024, it's only fitting to take a moment to reflect on the roller coaster ride that was the past year. For me, 2023 was a year of firsts, failures, friendships, and a whole lot of learning. Join me as I navigate through the highlights of my journey. One of the most significant milestones of 2023 was diving headfirst into the realm of entrepreneurship. So me and my buddy Beni decided to dip our toes into the whole entrepreneurship thing. Long story short, we started a project that actually brought in some cash. Not bad for a couple of rookies, huh? Learning became a constant companion throughout the year. From honing technical skills to exploring new areas of interest, 2023 was a chapter of intellectual growth for me. 2023 was like a crash course in everything. I'm talking about leveling up my skills, exploring random stuff, and basically turning myself into a mini expert in, like, 100 different things. Learning was the name of the game, and damn, it was a wild ride. The tapestry of life is woven with the threads of relationships, and 2023 introduced me to an array of new friends. Met some cool-ass people along the way. New friends, new vibes. Whether we clicked over some weird hobby or just shared a common hatred for Mondays, these connections added some serious flavor to my year. Decided my personal website needed a glow-up. Remade my personal website like I was on a mission. It's not just about looking good (although that's a bonus), but about showing off the real me—projects, wins(if I ever win anything), and the whole shebang. So, 2023, you crazy son of a gun. Thanks for the ups, the downs, and the messy in-betweens. Each curveball taught me something, and I'm heading into 2024 with some battle scars and a big ol' grin. Here's to more adventures, more growth, and less boring shit. Cheers to the next chapter! 🚀✌️ "2024 gon be our year fr" "Bismillah menang LKS"