Skip to main content

Installation Steps

1

Install BAML VSCode/Cursor Extension

Install the extension from: https://marketplace.visualstudio.com/items?itemName=boundary.baml-extensionFeatures include:
  • Syntax highlighting
  • Testing playground
  • Prompt previews
2

Install BAML CLI and Initialize Project

Install the BAML CLI tool globally and create starter BAML code:
go install github.com/boundaryml/baml/baml-cli@latest && baml-cli init
This 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
3

Install BAML Go Runtime

Install the Go runtime library:
go get github.com/boundaryml/baml
4

Install Required Go Tools

The BAML generator uses gofmt and goimports to format generated code:
# 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.
5

Generate the baml_client Package

One of the files in your baml_src directory will have a generator block. Run this command to auto-generate the baml_client directory with Go code:
baml-cli generate
Any types defined in .baml files will be converted into Go structs.
If you have the VSCode extension installed, it will automatically run baml-cli generate when you save a BAML file.
6

Use BAML Functions in Go

Import and use your generated BAML client:
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)
    }
    
    if value.IsFinal && value.Final() != nil {
      final := *value.Final()
      return &final, nil
    }
  }
  
  return nil, fmt.Errorf("stream ended without final response")
}

Build Integration

You can modify your build process to always call baml-cli generate before building:
Makefile
.PHONY: generate build

generate:
	baml-cli generate

build: generate
	go build ./...

test: generate
	go test ./...

Working with Go Modules

BAML integrates seamlessly with Go modules. Ensure your go.mod includes the BAML dependency:
go.mod
module example.com/myproject

go 1.21

require (
    github.com/boundaryml/baml v0.203.1
)
The generated baml_client package uses your module path:
import (
    b "example.com/myproject/baml_client"
    "example.com/myproject/baml_client/types"
)

Context and Cancellation

All BAML Go functions require a context.Context as the first parameter:
// 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")
}

Build docs developers (and LLMs) love