fern/01-guide/02-languages/go.mdx
To set up BAML with Go do the following:
<Steps> ### Install BAML VSCode/Cursor Extension https://marketplace.visualstudio.com/items?itemName=boundary.baml-extension - syntax highlighting
- testing playground
- prompt previews
```bash go
go install github.com/boundaryml/baml/baml-cli@latest && baml-cli init
```
This command will:
1. Install the BAML CLI tool globally
2. Create starter BAML code in a `baml_src` directory
3. Set up the basic project structure
After initializing your project, install the Go runtime library:
```bash go
go get github.com/boundaryml/baml
```
The BAML generator uses `gofmt` and `goimports` to format the generated Go code. Install these tools:
```bash go
# gofmt comes with Go by default, but install goimports
go install golang.org/x/tools/cmd/goimports@latest
```
These tools are required by the `on_generate` command in your generator configuration and ensure the generated code is properly formatted.
baml_client Go package from .baml filesOne of the files in your `baml_src` directory will have a [generator block](/ref/baml/generator). This tells BAML how to generate the `baml_client` directory, which will have auto-generated Go code to call your BAML functions.
Any types defined in .baml files will be converted into Go structs in the `baml_client` directory.
```bash
baml-cli generate
```
You can modify your build process to always call baml-cli generate before building.
```makefile Makefile
.PHONY: generate build
generate:
baml-cli generate
build: generate
go build ./...
test: generate
go test ./...
```
See [What is baml_client](/guide/introduction/baml_client) to learn more about how this works.
<Tip>
If you set up the [VSCode extension](https://marketplace.visualstudio.com/items?itemName=Boundary.baml-extension), it will automatically run `baml-cli generate` on saving a BAML file.
</Tip>
<Error>If `baml_client` doesn't exist, make sure to run the previous step! </Error>
```go main.go
package main
import (
"context"
"fmt"
"log"
b "example.com/myproject/baml_client"
"example.com/myproject/baml_client/types"
)
func main() {
ctx := context.Background()
// BAML's internal parser guarantees ExtractResume
// to always return a Resume type or an error
resume, err := b.ExtractResume(ctx, rawResume)
if err != nil {
log.Fatal(err)
}
fmt.Printf("Extracted resume: %+v\n", resume)
}
func exampleStream(rawResume string) (*types.Resume, error) {
ctx := context.Background()
stream, err := b.Stream.ExtractResume(ctx, rawResume)
if err != nil {
return nil, err
}
for value := range stream {
if value.IsError {
return nil, value.Error
}
if !value.IsFinal && value.Stream() != nil {
partial := *value.Stream()
fmt.Printf("Partial: %+v\n", partial) // This will be a partial Resume type
}
if value.IsFinal && value.Final() != nil {
final := *value.Final()
return &final, nil // This will be a complete Resume type
}
}
return nil, fmt.Errorf("stream ended without final response")
}
```
BAML integrates seamlessly with Go modules. Make sure your go.mod file includes the BAML dependency:
module example.com/myproject
go 1.21
require (
github.com/boundaryml/baml v0.203.1
)
The generated baml_client package will use your module path, so you can import it as:
import (
b "example.com/myproject/baml_client"
"example.com/myproject/baml_client/types"
)
All BAML Go functions require a context.Context as the first parameter, allowing you to:
// Set timeouts
ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second)
defer cancel()
result, err := b.ExtractResume(ctx, resume)
// Handle cancellation
ctx, cancel := context.WithCancel(context.Background())
go func() {
time.Sleep(5 * time.Second)
cancel() // Cancel the request after 5 seconds
}()
result, err := b.ExtractResume(ctx, resume)
if errors.Is(err, context.Canceled) {
fmt.Println("Request was canceled")
}
You're all set! Continue on to the Deployment Guides for your language to learn how to deploy your BAML code or check out the Interactive Examples to see more examples.