Changes which may break some users are marked below with: ⚠️
Language
As a reminder, we have two ongoing language experiments since v0.15; a replacement for struct embedding and a rework of aliases. Please give these a try and report any issues or feedback!
The new try experiment
This experiment adds a try clause in comprehensions as well as the use of ? in field selectors. This addition to the language intends to provide a more concise syntax for handling optional fields without the risk of unintentionally swallowing errors.
You can try this experiment by following our how-to guide. For more information, see the proposal on GitHub and the spec change patch.
The new else comprehension clause
This change adds an optional else clause for CUE modules targetting the language version v0.16.0 or later. With this addition to the language, an if or for comprehension may be followed by an else clause which triggers when the comprehension produces zero values.
Note that this feature is not an experiment; it is available to any CUE module targetting the language version v0.16.0 or later.
You can try this feature by following our how-to guide. For more information, see the full patch which includes the changes to the spec, or read the pre-release version of the language spec.
Evaluator
A number of changes were made to improve support for using cue.Values concurrently; see Issue #2733 for more details and ongoing progress.
A number of panics and other bugs in the evaluator which were reported since v0.15.0 have been fixed; thank you to all who reported these.
cmd/cue
The global --verbose and --trace flags have been moved to the cue get go and cue trim commands respectively, as they were the only ones actually using those flags, and this could be confusing to users.
Fix a bug where loading ./...:pkgname could lead to loading directories with zero CUE files as instances, which could cause poor performance for CUE packages with multiple parent directories.
LSP server
Code Actions: two code actions are now provided, Add surrounding struct braces and Remove surrounding struct braces, which convert between
a: b: c
and
a: {
b: c
}
with the cursor on b.
Initial LSP support for editing embedded JSON files. This feature provides completions and hover-docs when editing JSON files which are embedded into CUE via the @embed attribute. A teaser video is available on YouTube. Support for embedded YAML files will appear soon.
Several bug fixes, including better behaviour for files and directories with spaces; improvements for value aliases (foo: L=x); LSP rename now provides placeholder text.
See our Getting Started wiki page for instructions on how to set it up with your editor.
Please report any bugs or missing features you encounter via the Issue tracker or via the #lsp channels on Discord or Slack.
Encodings
Add support for encoding YAML tags like key: !Custom value by using CUE attributes like key: "value" @yaml(,tag="!Custom").
Standard library
The net package adds CompareIP to compare two IP addresses, which can be useful for computing with IP ranges.
The net/http package adds Serve as an experimental API to listen on a port and serve HTTP requests.
The tool/file package adds Symlink to create symbolic links.
Go API
cue/ast gains the NewPredeclared and Ident.IsPredeclared to mark and detect identifiers referencing predeclared names like error or int rather than fields which may shadow those names in the current scope.
⚠️ cue/token.Compare now sorts absolute paths before relative ones, to ensure consistent behavior between Unix-like systems and Windows.
⚠️ The long-deprecated and hidden cue.Instance.Eval method is now removed.
Full list of changes since v0.16.0-alpha.1
- internal/core/export: fix self-referential lets for recursive definitions by @mvdan in c257634
- internal/core/compile: avoid double error for invalid optional references by @mpvl in c1be2bb
- update all dependencies by @mvdan in 9fb0173
- internal/core/adt: add regression test for error() in pattern constraint keys by @mvdan in 50a0a5e
- internal/core/adt: fix structural cycle hang with braced selectors by @mvdan in 36702fd
- cmd/cue: add and unskip tests for invalid task type errors by @mvdan in db4afc1
- internal/core/dep: fix stack overflow on recursive definitions in dep analysis by @mvdan in 0b49a54
- internal/core/dep,internal/core/export: fix stack overflow on recursive definitions by @mvdan in d0e2ab6
- tools/flow: skip phantom tasks from eliminated conditional branches by @mvdan in 7fb912e
- encoding/gocode: fix test by @rogpeppe in 98ca6e3
- internal/core: remove import path to instance mapping by @rogpeppe in b3d9ffc
- doc/spec: use "custom errors" instead of "user errors" by @myitcv in baf8302
- internal/ci: explicitly set contents permission by @myitcv in 7cde504
- lsp/eval: Add support for try-clauses and optional path components by @cuematthew in 62de631
- cue/testdata: update stats for comprehensions/try.txtar by @mvdan in 20c1149
- internal/core/adt: implement try expressions by @mpvl in f2e8299
- cue/build: integrate identifier resolution into Complete by @mpvl in 1aeb33e
- lsp/fscache: ignore ASTs which have no absolute positions by @cuematthew in 2585b3b
- cue/ast,cue/ast/astutil: add NewPredeclared and IsPredeclared for builtin references by @mpvl in 8405422
- internal/core/adt: fix else clause duplication in comprehension field splitting by @mvdan in 40356ab
- cue/load: improve error for major-only version packages outside a module by @mvdan in 7675369
- cmd/cue/cmd: add test coverage for absolute packages with cue cmd by @mvdan in f5e266a
- encoding/yaml: add support for YAML tags via
@yaml(,tag) attribute by @jonas-meyer in b1a58bd
- internal/astinternal: omit ILLEGAL tokens in debug print by @mpvl in 23736eb
- cue: clarify that Schema is only useful for Value.Subsume by @mvdan in bb18d7b
- lsp/cache: expand completion range of fields in json for double-quotes by @cuematthew in b1c63da
- all: start using "else" in comprehensions by @mvdan in 3f2f654
- tweak Claude's allow and deny settings further by @mvdan in ef6bb80
- internal/ci: disable checkout persist-credentials by default by @myitcv in 069eac9
- cue/load: do not load non-CUE directories as instances by @rogpeppe in a4d2a6f
- cue/load: add test case for non-package directories by @rogpeppe in 028411e
- cmd/cue: deflake cue_after test by @rogpeppe in 4504db0
- all: use reflect.TypeAssert in three more places by @mvdan in 58cbd0c
- cue/internal: Make ToFile optionally preserve StructLits by @cuematthew in ec3e289
- all: re-apply
go fix -any=false ./... after Go version bump by @mvdan in 8579c46
- lsp/cache: completions must not return null items list by @cuematthew in 75ee97a
- internal/core/export: fix panic in relPathLength for BinaryExpr by @mvdan in 788eeed
- tools/fix: use ast.Predeclared to avoid shadowing in value alias conversion by @mvdan in 08a7ec3
- cue/ast,cue/ast/astutil: add Predeclared sentinel for builtin references by @mvdan in 42cc85f
- tools/fix: add tests for value alias conversion when "self" is in scope by @mvdan in 3dacb0c
- cue/ast/astutil: fix false positive in label expression check for let clauses by @mvdan in a93bcc1
- cmd/cue/cmd: add failing test for issue #4202 by @mvdan in 0a4a11a
- internal/core/export: avoid let name collisions with dependency fields by @mvdan in f2b697a
- internal/core/export: add failing test for issue #4221 by @mvdan in b690442
- internal/core/adt: fix undefined field in comprehension with structural cycle by @mvdan in 225a1c4
- cue/testdata: add regression test for issue #4203 by @mvdan in e3eb948
- internal/core/adt: fix panic in memory reclamation by @mvdan in 355d6fd
- internal/core/adt: add else clause to comprehensions by @mpvl in 9e2dec3
- _scripts: add OpenSpec support for AI-assisted development by @mpvl in 6a78eff
- lsp/eval: fix field-value aliases by @cuematthew in 29d8be4
- lsp/eval: add test to show bad behaviour of aliases by @cuematthew in 3e6bee7
- internal/core/export: fix hidden identifier renaming in for clauses by @mvdan in 2fea4bc
- internal/core/export: add failing test for issue #4254 by @mvdan in c53993e
- cue/errors: avoid duplicate path in error list formatting by @mvdan in 487c072
- pkg/list/testdata: add regression test for issue #4171 by @mvdan in e977cfa
- internal/lsp: implement ConvertFromStruct code action by @cuematthew in f68f686
- internal/ci: bump actions/checkout and cue.dev/x/githubactions by @mvdan in f4d1d5a
- lsp/server: force-load all packages for completions within embedded files by @cuematthew in 5eb5ed9
- pkg/tools/http: remove valueMu mutex from http.Serve by @mpvl in 95ba1d2
- internal/core/runtime: add lock protection to loaded map by @mpvl in 6451728
- internal/core/adt: fix race condition in Vertex.Default() by @mpvl in 854a5b7
- internal/core/adt: use thread-safe WeakMap for regexp caching by @mpvl in c7797c1
- pkg/tools/http: experimental implementation of http.Serve by @mpvl in 0badd6d
- golps/protocol: introduce DocumentURI.Path method by @cuematthew in f04e0fb
- gopls/protocol: rename DocumentURI.Path to DocumentURI.FilePath by @cuematthew in d8eca4a
- lsp/eval: process field attributes and specialise queries for embeds by @cuematthew in eb192c6
- internal/lsp: model embedded files as packages by @cuematthew in fa8946f
- lsp/fscache: read json and yaml files as CUE by @cuematthew in 6825394
- lsp/cache: rework package dirtying and reloading by @cuematthew in 22fff24
- internal/lsp: FileEvaluatorForURI returns lsp/cache.File by @cuematthew in dbf3293
- lsp/eval: change eval constructor to take Config struct by @cuematthew in 3cd3244
- interpreter/embed: prepare embed for extension by @cuematthew in a95414a
- encoding/json: extract PatchExpr to internal/encoding/json by @cuematthew in e5bfcda
- all: apply the straightforward Go 1.25 or later cleanups by @mvdan in e834a18
- cmd/cue: rewrite help fmt by @mvdan in 0fa24af
- all: test and release on Go 1.26, require Go 1.25 or later by @mvdan in 0dc0eac
- internal/core/compile: fix operator precedence in error() builtin by @mvdan in 70b3f3e
- cue/testdata/builtins: add test for error() with erroring interpolation by @mvdan in a6070c8
- internal/core/adt: fix value alias resolution in disjunctions by @mvdan in b053ad5
- cue/testdata/disjunctions: add regression test for value alias in disjunction by @mvdan in 0c9ed36
- internal/core/adt: handle EqualOp in SimplifyBounds by @mvdan in 0813460
- pkg/net: add CompareIP by @mvdan in 174a8b9
- pkg/encoding/openapi: support marshalSchema builtin for openAPI by @mpvl in 66ea772
- lsp/fscache: correct path components by @cuematthew in 44a543b
- integration/workspace: add test showing bad behaviour by @cuematthew in c164d8f
- add
go tool cue and xargs as allowed Claude commands by @mvdan in 4b495fa
- all: go fix -any=false ./... by @mvdan in 3d3f74b
- internal/lsp: implement ConvertToStruct code action by @cuematthew in c45f72d
- internal/core/adt: refine cycle handling in LetReference.resolve by @mvdan in 3e1e745
- cue/testdata/cycle: add regression test for issue 4244 by @mvdan in eb2c57c
- lsp/cache: provide placeholder for PrepareRename by @cuematthew in 049d6e1
- internal/ci: allow steps to influence job permissions by @myitcv in 839f03d
- cmd/cue: alter flag behavior based on the command name by @mvdan in bc5bd8f
- cmd/cue: drop --verbose and --trace as global flags by @mvdan in 92afa2e
- cmd/cue: map constants by go/types.Type directly by @mvdan in dac4e90
- pkg/tool/file: add Symlink by @sprat in 6618a6f
- internal/ci: fix release workflow by @myitcv in 9e34d67
- internal/ci: use new registry-login-action by @myitcv in f595566
- cue/token: sort absolute positions before relative ones by @mvdan in 46c1f9d
- cmd/cue: test that
cue fmt also formats files with no package clause by @mvdan in d65c829
- cue: remove Instance.Eval by @mvdan in 60c0505
- pkg/path: remove osInfo.HasPrefix by @mvdan in 516099a
- cmd/cue: rewrite help vet by @mvdan in 9488f0c
- cue: point out cue/format exists in the godoc by @mvdan in ba2ce99