Go è un linguaggio di programmazione compilato di Google, creato nel 2009 da Robert Griesemer, Rob Pike e Ken Thompson. Go combina la semplicità della sintassi con prestazioni a livello C. Nello sviluppo mobile, Go viene usato per backend, microservizi, gateway API e utilità CLI. Secondo Stack Overflow Survey (2025), Go è tra i dieci linguaggi di programmazione più remunerativi.
Punti chiave
Go è un linguaggio compilato a tipizzazione statica con gestione automatica della memoria tramite garbage collector. I principali obiettivi di Go: compilazione veloce, semplicità del codice e supporto integrato alla concorrenza. Go si compila in un binario nativo senza macchina virtuale — un singolo file eseguibile contiene tutto, incluse le dipendenze.
La libreria standard di Go copre server HTTP, marshaling JSON, parsing di flag da riga di comando, crittografia e operazioni sui database. Non serve alcun framework esterno per un server HTTP — net/http è integrato. Go Modules (da v1.16) è il sistema di gestione delle dipendenze standard. La versione attuale è Go 1.23 (2025) con un pacchetto iter migliorato per gli iteratori.
Go è stato progettato per risolvere i problemi di scalabilità affrontati da Google: compilazione lenta di C++, complessità di Java, concorrenza inefficiente di Python. Il risultato è un linguaggio che alimenta Docker, Kubernetes, Prometheus, Terraform e Hugo.
Go è minimalista: 25 parole chiave (contro 84 in C++). Niente classi, ereditarietà, generici (fino a v1.18), overload degli operatori o eccezioni. Gli errori vengono gestiti esplicitamente tramite ritorno di err. Strutture e interfacce sostituiscono la POO.
package main
import (
"encoding/json"
"fmt"
"net/http"
)
type User struct {
ID int `json:"id"`
Name string `json:"name"`
Email string `json:"email"`
}
func userHandler(w http.ResponseWriter, r *http.Request) {
w.Header().Set("Content-Type", "application/json")
user := User{ID: 1, Name: "Alice", Email: "alice@example.com"}
json.NewEncoder(w).Encode(user)
}
func main() {
http.HandleFunc("/api/user", userHandler)
fmt.Println("Server on :8080")
http.ListenAndServe(":8080", nil)
}La struttura User con tag JSON definisce la serializzazione. http.HandleFunc registra un gestore. json.NewEncoder(w).Encode(user) serializza la struttura in JSON direttamente nella risposta. Il server HTTP integrato gestisce le richieste in goroutine separate automaticamente.
Goroutines sono thread di esecuzione leggeri gestiti dal runtime di Go. A differenza dei thread del sistema operativo (1–8 MB di stack), una goroutine parte con 4 KB di stack che cresce dinamicamente. Si possono eseguire 100.000 goroutine su un singolo server. Avviare una goroutine — go functionName().
Canali (channels) sono code tipizzate per trasferire dati tra goroutine. Un canale viene creato tramite make(chan Type). L'operatore <- invia dati, <-chan riceve. I canali possono essere bufferizzati (con capacità) o non bufferizzati (sincroni).
package main
import (
"fmt"
"net/http"
"time"
)
func fetchURL(url string, ch chan<- string) {
start := time.Now()
resp, err := http.Get(url)
if err != nil {
ch <- fmt.Sprintf("Error: %s", err)
return
}
defer resp.Body.Close()
elapsed := time.Since(start)
ch <- fmt.Sprintf("%s — %dms", url, elapsed.Milliseconds())
}
func main() {
urls := []string{"https://google.com", "https://github.com", "https://stackoverflow.com"}
ch := make(chan string, len(urls))
for _, url := range urls {
go fetchURL(url, ch)
}
for range urls {
fmt.Println(<-ch)
}
}Tre richieste vengono eseguite concorrentemente tramite go fetchURL. Il canale ch raccoglie i risultati. defer resp.Body.Close() garantisce la chiusura della risposta all'uscita dalla funzione. select {} non viene usato poiché tutte le goroutine inviano al canale — la goroutine principale legge esattamente len(urls) volte.
Go è uno dei migliori linguaggi per il backend di applicazioni mobili. HTTP/2 e HTTP/3 integrati, serializzazione veloce con protobuf/gRPC e basso consumo di memoria rendono Go ideale per API che servono migliaia di client mobili.
Framework popolari: Gin (fino a 10x più veloce di Express.js), Echo (minimalista, middleware JWT), Fiber (stile Express), Chi (compatibile con net/http). Gin è il più popolare con 70k+ stelle su GitHub. Per gRPC si usa google.golang.org/grpc.
package main
import (
"database/sql"
"log"
"net/http"
"time"
"github.com/gin-gonic/gin"
_ "github.com/mattn/go-sqlite3"
)
func main() {
db, err := sql.Open("sqlite3", "mobile_app.db")
if err != nil {
log.Fatal(err)
}
defer db.Close()
r := gin.Default()
r.GET("/api/v1/posts", func(c *gin.Context) {
type Post struct {
ID int `json:"id"`
Title string `json:"title"`
CreatedAt time.Time `json:"created_at"`
}
rows, _ := db.Query("SELECT id, title, created_at FROM posts ORDER BY created_at DESC LIMIT 20")
defer rows.Close()
var posts []Post
for rows.Next() {
var p Post
rows.Scan(&p.ID, &p.Title, &p.CreatedAt)
posts = append(posts, p)
}
c.JSON(http.StatusOK, posts)
})
r.Run(":8080")
}Gin.GET registra una route con un gestore. sql.Open apre un database SQLite, db.Query esegue una query. c.JSON serializza lo slice posts in un array JSON. La funzione anonima all'interno di GET cattura db dal contesto esterno. Gin gestisce i panic, registra le richieste e supporta middleware.
Go è il linguaggio principale per l'architettura a microservizi. Il basso consumo di memoria per microservizio (15–30 MB) permette di eseguire dozzine di servizi su un singolo server. Avvio rapido (millisecondi) e dimensioni ridotte del binario (10–20 MB) semplificano il deployment in container.
Un gateway API in Go aggrega le richieste da un'app mobile ai servizi interni. Un gateway Go gestisce autenticazione (JWT), rate limiting, routing e caching. Implementazioni popolari: Kong (basato su OpenResty con plugin Go), Tyk (in Go), gateway personalizzati su Gin.
gRPC è un framework di chiamata di procedura remota di Google che utilizza Protocol Buffers per la serializzazione e HTTP/2 per il trasporto. Go ha il miglior supporto gRPC tra tutti i linguaggi. Per i backend mobili, gRPC fornisce una produttività 5–10 volte superiore a REST/JSON.
package main
import (
"context"
"log"
"net"
"google.golang.org/grpc"
pb "example.com/proto"
)
type server struct {
pb.UnimplementedUserServiceServer
}
func (s *server) GetUser(ctx context.Context, req *pb.GetUserRequest) (*pb.UserResponse, error) {
return &pb.UserResponse{
Id: req.Id,
Name: "Alice",
Email: "alice@example.com",
}, nil
}
func main() {
lis, _ := net.Listen("tcp", ":50051")
s := grpc.NewServer()
pb.RegisterUserServiceServer(s, &server{})
log.Fatal(s.Serve(lis))
}pb.UnimplementedUserServiceServer è uno stub generato da protoc dal file .proto. La struttura server sovrascrive il metodo GetUser. grpc.NewServer() crea un server con interceptor per logging, autenticazione e metriche.
Go è il miglior linguaggio per utilità CLI usate nello sviluppo mobile. Un singolo binario statico (~10 MB) senza dipendenze funziona su tutte le piattaforme: macOS, Linux, Windows. La compilazione richiede secondi. Le utilità Go non necessitano di installazione di interprete o runtime.
Esempi di strumenti Go nell'ecosistema mobile: Migrate (migrazioni DB), Kubectl (Kubernetes per backend mobile), Terraform (infrastruttura), Prometheus (monitoraggio). Gli sviluppatori scrivono utilità Go per generare modelli da file proto, validare configurazioni e distribuire microservizi.
package main
import (
"flag"
"fmt"
"os"
)
func main() {
project := flag.String("project", "", "Project directory")
version := flag.String("version", "1.0.0", "App version")
verbose := flag.Bool("verbose", false, "Verbose output")
flag.Parse()
if *project == "" {
fmt.Println("Usage: deploy --project=path [--version=x.x.x]")
os.Exit(1)
}
if *verbose {
fmt.Printf("Deploying project %s version %s\n", *project, *version)
}
// qui la logica di deployment
fmt.Println("Deploy complete")
}flag.String definisce un flag da riga di comando di tipo stringa con nome, valore predefinito e descrizione. flag.Parse() analizza gli argomenti os.Args. I puntatori *project vengono dereferenziati per ottenere i valori. Il binario viene compilato con go build -o deploy deploy.go.
Gomobile è uno strumento Google per compilare codice Go in librerie mobili native. go bind -target=android genera .aar per Android, go bind -target=ios genera .xcframework per iOS. Questo permette di scrivere logica di business comune in Go e chiamarla da Kotlin e Swift.
Casi d'uso principali di Gomobile: crittografia (schemi di cifratura personalizzati), rete (protocollo WebSocket personalizzato), elaborazione dati (compressione, codifica, parsing). L'interfaccia utente non viene scritta in Go — il suo scopo è sostituire C++ per moduli nativi multipiattaforma.
package mobile
import "crypto/aes"
// EncryptData crittografa i dati con AES-256-GCM (esportato in .aar)
func EncryptData(key []byte, plaintext []byte) ([]byte, error) {
block, err := aes.NewCipher(key)
if err != nil {
return nil, err
}
ciphertext := make([]byte, len(plaintext))
block.Encrypt(ciphertext, plaintext)
return ciphertext, nil
}
func DecryptData(key []byte, ciphertext []byte) ([]byte, error) {
block, err := aes.NewCipher(key)
if err != nil {
return nil, err
}
plaintext := make([]byte, len(ciphertext))
block.Decrypt(plaintext, ciphertext)
return plaintext, nil
}Le funzioni esportate (maiuscole) vengono incapsulate da Gomobile in interfacce Java/Swift. Da Kotlin, la chiamata appare come Mobile.encryptData(key, plaintext). Gomobile converte automaticamente i tipi: []byte → byte[] (Java) / Data (Swift).
| Comando | Risultato | Piattaforma |
|---|---|---|
| gomobile bind -target=android | Libreria .aar | Android |
| gomobile bind -target=ios | .xcframework | iOS |
| gomobile build -target=android | .apk con attività Go | Android |
Go compete con Java e Kotlin nello sviluppo server. Differenze chiave: Go si compila in un binario nativo, non richiede JVM, consuma 2–3 volte meno memoria e si avvia in millisecondi. Java vince per maturità dell'ecosistema e quantità di librerie.
| Criterio | Go | Java / Kotlin |
|---|---|---|
| Compilazione | Binario nativo (~10 MB) | Bytecode JVM + JIT |
| Avvio | 1–5 ms | 1–5 s (avvio JVM) |
| Consumo RAM | 15–30 MB per servizio | 50–200 MB per servizio |
| Concorrenza | Goroutines (integrate) | Coroutine / RxJava |
| Ecosistema | In crescita, 100k+ repository | Maturo, milioni di librerie |
| Apprendimento | 2–4 settimane | 6–12 mesi (Java) |
Go viene scelto per microservizi, gateway API e strumenti. Java/Kotlin — per applicazioni enterprise con logica di business ricca. Nello sviluppo mobile, la combinazione ottimale è: Go per backend, Kotlin/Swift per il client.
Domande frequenti
Go si compila in un unico binario statico senza JVM, consuma meno memoria e si avvia più velocemente. L'asincronia tramite goroutine è più semplice di RxJava o delle coroutine Kotlin. Per i microservizi, Go viene scelto per la sua semplicità e prestazioni.
I più popolari: Gin (alte prestazioni), Echo (minimalista), Fiber (stile Express.js), Chi (leggero e compatibile). Per il tempo reale si usa WebSocket Gorilla o Melody. Per gRPC — google.golang.org/grpc.
Sì, tramite Gomobile si può compilare Go in .aar (Android) e .xcframework (iOS). Tuttavia, l'interfaccia utente non viene scritta in Go — non è pratico a causa dell'ecosistema limitato. Go è efficace per librerie native, crittografia e rete.
Sì, Go è stato progettato per sistemi ad alto carico. Aziende come Cloudflare, Uber, Twitch, Dropbox usano Go in produzione. Lo scheduler di goroutine integrato gestisce milioni di attività concorrenti su un singolo server.
Go è più semplice di Java — non ha classi, ereditarietà o eccezioni. La sintassi è minimalista, strutture e interfacce sostituiscono la POO. La maggior parte degli sviluppatori impara Go in 2–4 settimane.
Riepilogo
Svilupperemo un'applicazione mobile chiavi in mano
IT Sectr crea applicazioni iOS e Android per startup e aziende dal 2017. Ti consulteremo e ti proporremo la soluzione migliore.
Leggi anche