render

package
v0.3.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jul 20, 2026 License: MIT Imports: 8 Imported by: 0

Documentation

Overview

Package render provides provider-agnostic interfaces for asynchronous (batch) avatar video generation: submit narration audio or a script, poll for completion, and download a talking-head video.

This is the offline counterpart to package live, which handles real-time streaming avatar sessions.

The typical flow is:

job, err := provider.Generate(ctx, render.GenerateRequest{
    AvatarID: avatarID,
    AudioURL: narrationURL,
})
status, err := render.Wait(ctx, provider, job.ID, 5*time.Second)
err = provider.Download(ctx, job.ID, outFile)

Index

Constants

View Source
const DefaultPollInterval = 3 * time.Second

DefaultPollInterval is the polling interval used by Wait when the caller passes a non-positive interval.

Variables

View Source
var (
	// ErrAudioUploadUnsupported indicates that the provider cannot host
	// audio files; callers must supply GenerateRequest.AudioURL.
	ErrAudioUploadUnsupported = errors.New("render: audio upload unsupported")

	// ErrInvalidRequest indicates that the request failed validation
	// before submission (e.g., neither or both of AudioURL/Script set,
	// missing AvatarID).
	ErrInvalidRequest = errors.New("render: invalid request")

	// ErrJobNotFound indicates that the provider does not recognize the
	// job ID.
	ErrJobNotFound = errors.New("render: job not found")

	// ErrJobFailed indicates that the job reached JobStateFailed.
	ErrJobFailed = errors.New("render: job failed")

	// ErrJobNotCompleted indicates that Download was called before the
	// job completed successfully.
	ErrJobNotCompleted = errors.New("render: job not completed")

	// ErrProviderUnavailable indicates that the provider API is
	// unreachable or returned an unexpected error.
	ErrProviderUnavailable = errors.New("render: provider unavailable")

	// ErrProviderAuthFailed indicates that authentication with the
	// provider failed (invalid API key, etc.).
	ErrProviderAuthFailed = errors.New("render: provider authentication failed")

	// ErrInvalidConfig indicates that the provider configuration is
	// invalid or incomplete.
	ErrInvalidConfig = errors.New("render: invalid configuration")
)

Sentinel errors for render operations.

Functions

func AudioContentType added in v0.3.0

func AudioContentType(filename string) string

AudioContentType guesses a MIME type from an audio filename extension, for use by AudioUploader implementations. Unknown extensions return "application/octet-stream".

func DownloadURL added in v0.3.0

func DownloadURL(ctx context.Context, client *http.Client, url string, dst io.Writer) error

DownloadURL streams the content at url to dst using client, a helper for implementing Provider.Download from a completed job's video URL. A nil client uses http.DefaultClient. Cancellation is via ctx.

Types

type AudioUploader

type AudioUploader interface {
	// UploadAudio uploads audio content and returns a URL usable as
	// GenerateRequest.AudioURL with the same provider.
	UploadAudio(ctx context.Context, filename string, r io.Reader) (string, error)
}

AudioUploader is an optional capability for providers that can host local audio files. Callers should feature-detect:

if up, ok := provider.(render.AudioUploader); ok {
    url, err = up.UploadAudio(ctx, "narration.mp3", f)
}

Providers without hosting support do not implement this interface; callers must supply a publicly fetchable GenerateRequest.AudioURL.

type AvatarInfo added in v0.3.0

type AvatarInfo struct {
	// ID is directly usable as GenerateRequest.AvatarID with the same
	// provider.
	ID string

	// Name is the human-readable avatar name.
	Name string

	// Gender is the avatar gender, when the provider reports it.
	Gender string
}

AvatarInfo describes an avatar available from a render provider, discovered via AvatarLister.

type AvatarLister added in v0.3.0

type AvatarLister interface {
	// ListAvatars returns avatars whose ID or name matches search
	// (case-insensitive substring; an empty search returns all).
	ListAvatars(ctx context.Context, search string) ([]AvatarInfo, error)
}

AvatarLister is an optional capability for render providers that can enumerate the avatars available to the account. Callers feature-detect it, like AudioUploader:

if l, ok := provider.(render.AvatarLister); ok {
    avatars, err := l.ListAvatars(ctx, "")
}

The returned AvatarInfo.ID values are directly usable as GenerateRequest.AvatarID with the same provider — useful because a provider's avatar-listing endpoint may return different identifiers than its generation endpoint accepts (HeyGen's v3 avatar groups vs. v2 avatar IDs, for example).

type Background

type Background struct {
	// Type is "color", "image", or "video".
	Type string

	// Value is a hex color or URL depending on Type.
	Value string
}

Background describes the requested video background.

type GenerateRequest

type GenerateRequest struct {
	// AvatarID identifies the presenter with the provider.
	// HeyGen: avatar_id; Tavus: replica_id; bitHuman: agent_id.
	AvatarID string

	// AudioURL is a fetchable URL to narration audio (.mp3/.wav).
	// Providers implementing AudioUploader can host local files.
	AudioURL string

	// Script is text for provider TTS. Providers that require a voice
	// read it from Extensions (e.g., "voice_id").
	Script string

	// Width and Height are the requested output dimensions in pixels.
	// Optional; provider defaults apply when zero.
	Width int

	// Height is the requested output height in pixels.
	Height int

	// Background requests a background treatment. Optional and
	// best-effort; support varies by provider.
	Background *Background

	// Title is a human-readable job/video name. Optional.
	Title string

	// Extensions holds provider-specific options
	// (e.g., "voice_id", "avatar_style", "test", "fast").
	Extensions map[string]any
}

GenerateRequest describes an avatar video generation job.

Exactly one of AudioURL or Script must be set. AudioURL is the design center: it drives lip-sync from existing narration audio so the avatar matches the authoritative audio track exactly. Script uses provider TTS instead and is a secondary path.

func (GenerateRequest) GetBool

func (r GenerateRequest) GetBool(key string, defaultValue bool) bool

GetBool retrieves a bool extension value with a default.

func (GenerateRequest) GetString

func (r GenerateRequest) GetString(key, defaultValue string) string

GetString retrieves a string extension value with a default.

func (GenerateRequest) Validate

func (r GenerateRequest) Validate() error

Validate checks that the request is well-formed. It returns an error wrapping ErrInvalidRequest if AvatarID is empty, or if neither or both of AudioURL and Script are set.

type Job

type Job struct {
	// ID is the provider job/video identifier.
	ID string

	// Provider is the provider name (e.g., "heygen", "tavus", "bithuman").
	Provider string
}

Job identifies a submitted generation job.

type JobState

type JobState string

JobState is the normalized lifecycle state of a generation job.

Providers map their native status strings onto these states; the native string is preserved in JobStatus.RawStatus. Unknown provider states map to JobStateProcessing (non-terminal, safe for pollers).

const (
	// JobStatePending indicates the job is queued but not yet started.
	JobStatePending JobState = "pending"

	// JobStateProcessing indicates the provider is generating the video.
	JobStateProcessing JobState = "processing"

	// JobStateCompleted indicates the video is ready for download.
	JobStateCompleted JobState = "completed"

	// JobStateFailed indicates generation failed.
	JobStateFailed JobState = "failed"
)

func (JobState) Terminal

func (s JobState) Terminal() bool

Terminal reports whether the state is final.

type JobStatus

type JobStatus struct {
	// ID is the provider job/video identifier.
	ID string

	// State is the normalized lifecycle state.
	State JobState

	// RawStatus is the provider-native status string, preserved for
	// logging and debugging.
	RawStatus string

	// VideoURL is the download URL, set when State is JobStateCompleted.
	// It may be a time-limited signed URL; use Provider.Download for a
	// fresh URL.
	VideoURL string

	// ThumbnailURL is a preview image URL, when the provider reports one.
	ThumbnailURL string

	// Duration is the video duration in seconds, when reported.
	Duration float64

	// ErrorCode is the provider error code, when State is JobStateFailed.
	ErrorCode string

	// ErrorMsg is the provider error message, when State is JobStateFailed.
	ErrorMsg string
}

JobStatus is a point-in-time snapshot of a job.

func Wait

func Wait(ctx context.Context, p Provider, jobID string, interval time.Duration) (*JobStatus, error)

Wait polls p.Status until the job reaches a terminal state, the context is cancelled, or a Status call fails. An interval <= 0 defaults to DefaultPollInterval.

If the job reaches JobStateFailed, Wait returns the final status AND an error wrapping ErrJobFailed, so callers can inspect ErrorCode and ErrorMsg while still using errors.Is.

type Provider

type Provider interface {
	// Name returns the provider name (e.g., "heygen", "tavus", "bithuman").
	Name() string

	// Generate submits a video generation job. It returns as soon as the
	// provider accepts the job; use Status or Wait to track completion.
	Generate(ctx context.Context, req GenerateRequest) (*Job, error)

	// Status returns the current status of a job.
	Status(ctx context.Context, jobID string) (*JobStatus, error)

	// Download streams the completed video to dst.
	// Returns an error wrapping ErrJobNotCompleted if the job has not
	// completed successfully.
	Download(ctx context.Context, jobID string, dst io.Writer) error
}

Provider generates avatar videos asynchronously.

Implementations of this interface handle provider-specific API calls to submit generation jobs, poll their status, and download results. Each provider (HeyGen, Tavus, bitHuman, etc.) has its own Provider implementation.

type ProviderError

type ProviderError struct {
	Provider string // Provider name (e.g., "heygen", "tavus")
	Op       string // Operation that failed
	Err      error  // Underlying error
}

ProviderError wraps an error from a render provider with additional context.

func NewProviderError

func NewProviderError(provider, op string, err error) *ProviderError

NewProviderError creates a new ProviderError.

func (*ProviderError) Error

func (e *ProviderError) Error() string

Error implements the error interface.

func (*ProviderError) Unwrap

func (e *ProviderError) Unwrap() error

Unwrap returns the underlying error.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL