Status: EXTERNAL BETA RELEASE
Python is incredibly popular and would be an easy starting point for many developers. Its vast ecosystem, readable syntax, and extensive libraries make it a natural first choice. However, after careful consideration, we chose Go for this SDK. Here's why:
One of Python's biggest challenges is deployment complexity. Running Python reliably across Windows, macOS, Linux, and cloud environments requires managing:
- Python interpreter installation - Ensuring the correct Python version is available on each target system
- Virtual environments - Isolating dependencies per project to avoid conflicts
- Dependency resolution - Managing pip, requirements.txt, and potential version conflicts between packages
- Platform-specific issues - Some packages require different installation procedures or have OS-specific dependencies
As noted in the Python community, dependency management can be challenging, and many teams resort to containerization just to achieve consistent deployments.
Go takes a different approach: compile once, run anywhere. The Go compiler produces a single, self-contained binary with no external dependencies. Deploy to Windows, Mac, Linux, or any cloud platform by simply copying one file. No runtime installation, no virtual environments, no dependency management on target systems.
Go was designed with simplicity in mind. Its small, consistent syntax means developers can become productive quickly. The language has:
- 25 keywords (compared to Python's 35+)
- One way to do things - Go's philosophy reduces decision fatigue
- Excellent documentation - The standard library is well-documented with runnable examples
- Built-in formatting -
go fmteliminates style debates
Go's concurrency primitives—goroutines and channels—provide an intuitive model for parallel operations. This is essential for an SDK that needs to:
- Handle multiple device connections simultaneously
- Process large batches of API requests efficiently
- Manage concurrent uploads and downloads
Python's Global Interpreter Lock (GIL) limits true parallelism, making concurrent I/O-bound operations more complex to implement correctly.
Modern AI assistants and LLMs are remarkably proficient at generating Go code. This is increasingly important as developers leverage AI tools for productivity. Go's characteristics make it particularly well-suited for AI-assisted development:
- Strong typing catches errors at compile time, providing immediate feedback on generated code
- Simple, consistent syntax means AI models produce more reliable output
- Comprehensive standard library reduces the need for third-party dependencies
- Clear error handling patterns result in more predictable generated code
As the Go team notes, Go is excellent for building LLM-powered applications, and the same qualities that make it good for using AI make it good for AI to write.
Go compiles to native machine code, delivering significantly better performance than interpreted Python for CPU-bound operations. For an SDK making hundreds of API calls, parsing large responses, and processing device data, this translates to faster execution and lower resource usage.
A comprehensive Go SDK providing type-safe access to BrightSign Network (BSN.cloud) APIs. Includes both the main REST API and Remote Diagnostic Web Server (RDWS) functionality with 64 working example programs.
This SDK abstracts the complexity of BSN.cloud integration:
- OAuth2 Authentication - Automatic token management and refresh
- Device Management - List, monitor, control, and provision BrightSign players
- Remote Operations - Screenshots, reboots, file management, diagnostics via RDWS
- B-Deploy Provisioning - Create and manage player setup configurations
- Network Management - Handle multiple networks, groups, permissions
Key Features:
- Full type safety - All nested types exported for compile-time checking and IDE autocomplete
- Device status monitoring - Type-safe access to firmware, network, storage, and sync information
- Screenshot capture - Request and response types for device snapshots with region support
- Structured error types with context
- Pagination support for large datasets
- Network context management with
BS_NETWORKenvironment variable support - Concurrent-safe token handling
- 64 example CLI tools demonstrating all features
- Flexible output modes (JSON, stdout, file) for automation and scripting
Recommended: Pin to a specific version
go get github.com/brightdevelopers/gopurple@v1.2.0Or use latest (development)
go get github.com/brightdevelopers/gopurpleIn your go.mod:
require github.com/brightdevelopers/gopurple v1.2.0See versioning docs for version management details.
package main
import (
"context"
"log"
"github.com/brightdevelopers/gopurple"
)
func main() {
// Create client (uses BS_CLIENT_ID and BS_SECRET env vars)
client, err := gopurple.New()
if err != nil {
log.Fatal(err)
}
ctx := context.Background()
// Authenticate and set network
if err := client.Authenticate(ctx); err != nil {
log.Fatal(err)
}
// List devices
devices, err := client.Devices.List(ctx, nil)
if err != nil {
log.Fatal(err)
}
log.Printf("Found %d devices", len(devices.Items))
}The SDK provides full type safety for device status information, including firmware, network, storage, and synchronization details:
// Get device with full status information
device, err := client.Devices.Get(ctx, "ABC123")
if err != nil {
log.Fatal(err)
}
// Access device status with full type safety
if device.Status != nil {
// Check firmware version
if device.Status.Firmware != nil {
log.Printf("Firmware: %s", device.Status.Firmware.Version)
}
// Check network connectivity
if device.Status.Network != nil {
log.Printf("IP: %s", device.Status.Network.ExternalIP)
for _, iface := range device.Status.Network.Interfaces {
log.Printf(" %s: %s", iface.Name, iface.Type)
}
}
// Monitor storage usage
for _, storage := range device.Status.Storage {
pct := float64(storage.Used) / float64(storage.Total) * 100
log.Printf("Storage: %.1f%% used", pct)
}
}Capture device screenshots with specific regions and quality settings:
// Take a full-screen screenshot
req := &gopurple.SnapshotRequest{
Format: "png",
Quality: 90,
}
resp, err := client.RDWS.Snapshot(ctx, "ABC123", req)
if err != nil {
log.Fatal(err)
}
log.Printf("Screenshot: %s (%dx%d)", resp.Filename, resp.Width, resp.Height)
// Capture specific region
regionReq := &gopurple.SnapshotRequest{
Format: "jpeg",
Quality: 85,
Region: &gopurple.Region{
X: 100,
Y: 100,
Width: 1920,
Height: 1080,
},
}Build device setup records with full compile-time type checking:
setup := &gopurple.BDeploySetupRecord{
Version: "1.0",
BDeploy: &gopurple.BDeployInfo{
// ... your B-Deploy configuration
},
IdleScreenColor: &gopurple.IdleScreenColor{
R: 0, G: 0, B: 0, A: 1, // Black idle screen
},
}Always pin to specific versions in production to ensure reproducible builds:
# Install specific version
go get github.com/brightdevelopers/gopurple@v1.2.0In your go.mod:
require github.com/brightdevelopers/gopurple v1.2.0# List all available versions
go list -m -versions github.com/brightdevelopers/gopurple
# View current installed version
go list -m github.com/brightdevelopers/gopurple
# View release notes
gh release list --repo brightdevelopers/gopurple# Update to specific version
go get github.com/brightdevelopers/gopurple@v1.3.0
# Update to latest version
go get -u github.com/brightdevelopers/gopurple
# Update to latest patch only (safer)
go get -u=patch github.com/brightdevelopers/gopurpleThe SDK follows Semantic Versioning 2.0.0:
- v1.x.x → v1.x.x - Backward compatible (safe to update)
- v1.x.x → v2.0.0 - Breaking changes (review migration guide)
- v1.x.x-beta.x - Pre-release versions (test before production)
Version compatibility:
# All v1 releases are compatible with each other
v1.0.0, v1.1.0, v1.2.0 ✅ Compatible
# Major version changes may require code updates
v1.x.x → v2.0.0 ⚠️ Review breaking changesGitHub Actions:
- name: Install gopurple
run: go get github.com/brightdevelopers/gopurple@v1.2.0Dockerfile:
FROM golang:1.24-alpine
WORKDIR /app
COPY go.mod go.sum ./
RUN go mod download
# gopurple version pinned in go.mod
COPY . .
RUN go build -o app# Create a new release
./scripts/release.sh v1.2.0 "Release Description"
# Create a pre-release
./scripts/release.sh v1.3.0-beta.1 "Beta: New Features"See RELEASING.md for the complete release process and docs/versioning.md for detailed version management documentation.
- Log into BSN.cloud
- Navigate to Admin → API Access
- Create new OAuth2 credentials
- Note your Client ID and Secret
export BS_CLIENT_ID=your_client_id
export BS_SECRET=your_client_secret
export BS_NETWORK=your_network_name # optionalOr configure programmatically:
client, err := gopurple.New(
gopurple.WithCredentials("client-id", "client-secret"),
gopurple.WithNetwork("Production"),
gopurple.WithTimeout(60*time.Second),
)The SDK includes 64 working example programs demonstrating all functionality. Each example is a standalone CLI tool you can use immediately.
See examples/README.md for complete documentation of all examples with usage instructions.
| Category | Count | Examples |
|---|---|---|
| Authentication | 2 | Token management, credential testing |
| B-Deploy Provisioning | 13 | Setup records, device association, template rendering, token generation |
| Device Management | 9 | List, status, errors, operations, group management |
| Group Management | 3 | Group info, updates, deletion |
| Subscription Management | 3 | Device subscriptions, counts, operations |
| Remote DWS (RDWS) | 34 | Remote control, diagnostics, file operations, screenshots |
# Build all examples
make build-examples
# List devices
./bin/main--devices-list --network Production
# Get device info via RDWS
./bin/rdws-info --serial BS123456789
# Capture screenshot
./bin/rdws-snapshot --serial BS123456789 --output screenshot.png
# Get device logs (flexible output modes)
./bin/rdws-logs-get --serial BS123456789 --logfile device.log # to file
./bin/rdws-logs-get --serial BS123456789 --stdout | grep ERROR # to stdout
./bin/rdws-logs-get --serial BS123456789 --json # as JSONExample configuration files are provided in multiple locations:
config.json- Basic B-Deploy setup configurationconfig-comprehensive.json- Full setup with all debugging/logging enabledconfig-wifi-example.json- Wireless network configuration exampleconfig-annotated.json- Annotated configuration showing all available options
The comprehensive configuration includes:
- Local DWS enabled with password protection
- Remote DWS enabled
- All logging types enabled (playback, event, diagnostic, state, variable)
- Serial and system log debugging enabled
- Remote screenshots enabled
- Network diagnostics enabled
bsn-control.json- BSN.cloud network control setup examplelfn-control.json- Local File Network (LFN) control setup example
example-config.json- Partial setup update exampleexample-full-update.json- Complete setup reconfiguration example
These show the JSON structure expected by various SDK methods and can be used as templates for your own configurations.
Note: SSH and Telnet must be enabled via RDWS after device provisioning.
Implementation Status: 43 of ~294 endpoints
See docs/all-apis.md for a comprehensive list of all BSN.cloud API endpoints with implementation status ([DONE] or [NOT-DONE]).
✅ Device Management (Complete)
- List devices with pagination, filtering, sorting
- Get device details, status, errors, operations
- Update device properties, change groups
- Delete devices
✅ Remote Diagnostic Web Server (RDWS) (Complete)
- Device info, health, time management
- Remote reboot (normal, crash, factory reset)
- Screenshots and diagnostics
- File operations (list, upload, download, delete, rename)
- Network diagnostics (ping, traceroute, DNS lookup)
- Registry operations (read, write)
- Log and crashdump retrieval
- Firmware downloads
- SSH/Telnet management
- Local DWS control
- Storage reformatting
✅ B-Deploy Provisioning (Complete)
- Create, update, delete setup records (struct-based and raw JSON)
- Associate devices with setups
- List and query provisioning configurations
- Template-based setup generation with dynamic token injection
- Raw JSON round-trip preserving all fields (firmware entries, network config)
✅ Group Management (Core Features)
- Get group information
- Update group properties
- Delete groups
✅ Subscription Management (Read Operations)
- List device subscriptions
- Get subscription counts
- Query permissions
See docs/all-apis.md for the complete list of unimplemented endpoints, including:
- Autorun/Plugin management
- Dynamic playlists
- Live text feeds
- Data feeds
- Device web pages
- Live media feeds
- Scheduled downloads
- Tag management
- User management
- Web folder management
- And more...
The SDK focuses on the most commonly used operations first. Additional endpoints can be added as needed.
graph TB
App[Your Application] --> Client[gopurple.Client]
Client --> Auth[Auth Manager]
Client --> HTTP[HTTP Client]
Client --> Services[Service Layers]
Auth --> Token[Token Management]
Auth --> Network[Network Context]
HTTP --> Retry[Retry Logic]
HTTP --> Error[Error Handling]
Services --> Devices[Device Service]
Services --> RDWS[RDWS Service]
Services --> BDeploy[B-Deploy Service]
HTTP --> BSN[BSN Main API<br/>api.bsn.cloud]
HTTP --> RDWS_API[Remote DWS API<br/>ws.bsn.cloud]
sequenceDiagram
participant App
participant Client
participant Auth
participant BSN as BSN.cloud
App->>Client: New()
Client->>Auth: NewAuthManager()
App->>Client: Authenticate(ctx)
Client->>Auth: Authenticate()
Auth->>BSN: POST /token (client_credentials)
BSN-->>Auth: access_token + expires_in
Auth-->>Client: success
App->>Client: SetNetwork(ctx, "MyNetwork")
Client->>Auth: SetNetwork()
Auth->>BSN: PUT /Self/Session/Network
BSN-->>Auth: 204 No Content
Auth-->>Client: network set
App->>Client: API Operation
Client->>Auth: GetToken()
Auth->>Auth: Check expiry
Auth-->>Client: valid token
Client->>BSN: API request with token
BSN-->>Client: response
Client-->>App: result
// List devices with filtering
params := &gopurple.DeviceListParams{
Filter: "model=XD1033",
Sort: "lastModifiedDate desc",
PageSize: 50,
}
devices, err := client.Devices.List(ctx, params)
// Get specific device
device, err := client.Devices.GetBySerial(ctx, "BS123456789")
// Change device group
err = client.Devices.Update(ctx, deviceID, &gopurple.DeviceUpdate{
GroupID: newGroupID,
})
// Delete device
err = client.Devices.Delete(ctx, deviceID)// Get device info
info, err := client.RDWS.GetInfo(ctx, serial)
// Capture screenshot
screenshot, err := client.RDWS.Snapshot(ctx, serial)
os.WriteFile("screenshot.png", screenshot, 0644)
// Reboot device
success, err := client.RDWS.Reboot(ctx, serial, "normal")
// List files on device
files, err := client.RDWS.ListFiles(ctx, serial, "/storage/sd/")
// Upload file to device
err = client.RDWS.UploadFile(ctx, serial, localPath, remotePath)// Create setup record from config
config := &types.BDeploySetupConfig{
NetworkName: "Production",
Username: "admin@example.com",
PackageName: "retail-display",
SetupType: "bsn",
Network: types.NetworkConfig{
TimeServers: []string{"time.bsn.cloud"},
Interfaces: []types.NetworkInterface{
{
ID: "eth0",
Type: "Ethernet",
Proto: "DHCPv4",
ContentDownloadEnabled: true,
HealthReportingEnabled: true,
},
},
},
}
setupID, err := client.BDeploy.CreateSetup(ctx, config)
// Associate device with setup
err = client.BDeploy.AssociateDevice(ctx, serial, setupID)devices, err := client.Devices.List(ctx, nil)
if err != nil {
if gopurple.IsAuthenticationError(err) {
log.Println("Auth failed - check credentials")
} else if gopurple.IsNetworkError(err) {
log.Println("Network issue - check connectivity")
} else if gopurple.IsRateLimitError(err) {
log.Println("Rate limited - retry later")
} else if gopurple.IsRetryableError(err) {
log.Println("Temporary error - will retry")
} else {
log.Printf("API error: %v", err)
}
return
}# Run all tests
make test
# Build all example programs
make build-examples
# Build specific example
make build-main--devices-list
# Clean build artifacts
make clean
# Run all (test + build)
make allgopurple/
├── gopurple.go # Main SDK client interface
├── internal/
│ ├── auth/ # OAuth2 authentication
│ ├── config/ # Configuration management
│ ├── errors/ # Error types
│ ├── http/ # HTTP client wrapper
│ ├── services/ # API service implementations
│ └── types/ # Data structures
├── templates/ # Setup template files
│ └── DefaultSetupPackageTemplateMaster.json # Master Go-template for B-Deploy setups
├── setups/ # Rendered setup templates
│ └── setup-template.json # Reference setup template
├── examples/ # 64 example CLI programs
│ ├── render-setup-template/ # Render template + generate token -> stdout
│ ├── generate-token-json/ # Generate registration token JSON
│ ├── bdeploy-add-setup-raw/ # Create setup from raw JSON (preserves all fields)
│ ├── bdeploy-add-setup/ # Create setup via Go struct
│ │ ├── config.json # Basic setup example
│ │ ├── config-comprehensive.json
│ │ └── config-wifi-example.json
│ ├── bdeploy-update-setup/
│ │ ├── example-config.json
│ │ └── example-full-update.json
│ ├── README.md # Complete examples documentation
│ └── ... (55+ more examples)
├── configs/ # Global configuration examples
│ ├── bsn-control.json
│ └── lfn-control.json
├── docs/
│ ├── all-apis.md # Complete API endpoint reference
│ ├── bdeploy-config-reference.md # B-Deploy configuration guide
│ ├── bdeploy-association.md # Device association documentation
│ └── need-json-out.md # Programs needing JSON output
├── images/
│ └── logo.png # Project logo
└── Makefile # Build targets
- Go 1.21+
- BSN.cloud API credentials (OAuth2 Client ID and Secret)
- Network access to:
auth.bsn.cloud(authentication)api.bsn.cloud(main API)ws.bsn.cloud(RDWS API)
This SDK prioritizes the most commonly used BSN.cloud operations. If you need additional endpoints:
- Check docs/all-apis.md to see if it's documented
- Look at existing service implementations in
internal/services/ - Follow the established patterns for consistency
- Add tests and example programs
- Update documentation
Creating releases:
./scripts/release.sh v1.2.0 "Release Description"See RELEASING.md for the complete release workflow and docs/versioning.md for version management guidelines.
This is an unofficial SDK for BSN.cloud integration.
- BSN.cloud Documentation: https://docs.brightsign.biz/
- Complete API Endpoint Reference: docs/all-apis.md
- Type Safety Guide: docs/type-safety.md
- Version Management: docs/versioning.md
- Release Process: RELEASING.md
- Example Programs Guide: examples/README.md
- B-Deploy Template Guide: docs/bdeploy-template.md
- B-Deploy Configuration Reference: docs/bdeploy-config-reference.md
- B-Deploy Device Association: docs/bdeploy-association.md
- Programs Needing JSON Output: docs/need-json-out.md
- BSN.cloud Admin Panel: https://bsn.cloud/
- GitHub Repository: https://github.com/brightdevelopers/gopurple
EXPERIMENTAL ONLY - This SDK is provided as-is for integration with BrightSign Network. While actively used in production, it is not officially supported by BrightSign LLC. Use at your own discretion.
