README: Cleanup examples to make them runnable and testable
This commit is contained in:
parent
c55bf62438
commit
f334ef5952
15 changed files with 159 additions and 61 deletions
50
README.md
50
README.md
|
|
@ -111,56 +111,8 @@ For detailed installation docs, with alternative methods and examples for each O
|
||||||
In addition to being a runnable CLI tool, D2 can also be used to produce diagrams from
|
In addition to being a runnable CLI tool, D2 can also be used to produce diagrams from
|
||||||
Go programs.
|
Go programs.
|
||||||
|
|
||||||
```go
|
For examples, see [./docs/examples/lib](./docs/examples/lib).
|
||||||
import (
|
|
||||||
"context"
|
|
||||||
"io/ioutil"
|
|
||||||
"path/filepath"
|
|
||||||
"strings"
|
|
||||||
|
|
||||||
"oss.terrastruct.com/d2/d2compiler"
|
|
||||||
"oss.terrastruct.com/d2/d2exporter"
|
|
||||||
"oss.terrastruct.com/d2/d2layouts/d2dagrelayout"
|
|
||||||
"oss.terrastruct.com/d2/d2renderers/d2svg"
|
|
||||||
"oss.terrastruct.com/d2/d2renderers/textmeasure"
|
|
||||||
"oss.terrastruct.com/d2/d2themes/d2themescatalog"
|
|
||||||
)
|
|
||||||
|
|
||||||
func main() {
|
|
||||||
graph, _ := d2compiler.Compile("", strings.NewReader("x -> y"), &d2compiler.CompileOptions{UTF16: true})
|
|
||||||
ruler, _ := textmeasure.NewRuler()
|
|
||||||
graph.SetDimensions(nil, ruler)
|
|
||||||
d2dagrelayout.Layout(context.Background(), graph)
|
|
||||||
diagram, _ := d2exporter.Export(context.Background(), graph, d2themescatalog.NeutralDefault.ID)
|
|
||||||
out, _ := d2svg.Render(diagram)
|
|
||||||
ioutil.WriteFile(filepath.Join("out.svg"), out, 0600)
|
|
||||||
}
|
|
||||||
```
|
|
||||||
|
|
||||||
D2 is built to be hackable -- the language has an API built on top of it to make edits
|
|
||||||
programmatically. Modifying the above diagram:
|
|
||||||
|
|
||||||
```go
|
|
||||||
import (
|
|
||||||
"oss.terrastruct.com/d2/d2renderers/textmeasure"
|
|
||||||
"oss.terrastruct.com/d2/d2themes/d2themescatalog"
|
|
||||||
)
|
|
||||||
|
|
||||||
// Create a shape with the ID, "meow"
|
|
||||||
graph, _, _ = d2oracle.Create(graph, "meow")
|
|
||||||
// Style the shape green
|
|
||||||
color := "green"
|
|
||||||
graph, _ = d2oracle.Set(graph, "meow.style.fill", nil, &color)
|
|
||||||
// Create a shape with the ID, "cat"
|
|
||||||
graph, _, _ = d2oracle.Create(graph, "cat")
|
|
||||||
// Move the shape "meow" inside the container "cat"
|
|
||||||
graph, _ = d2oracle.Move(graph, "meow", "cat.meow")
|
|
||||||
// Prints formatted D2 script
|
|
||||||
println(d2format.Format(graph.AST))
|
|
||||||
```
|
|
||||||
|
|
||||||
This makes it easy to build functionality on top of D2. Terrastruct uses the above API to
|
|
||||||
implement editing of D2 from mouse actions in a visual interface.
|
|
||||||
|
|
||||||
## Themes
|
## Themes
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -26,7 +26,7 @@
|
||||||
- `d2` now lives in the root folder of the repository instead of as a subcommand.
|
- `d2` now lives in the root folder of the repository instead of as a subcommand.
|
||||||
So you can run `go install oss.terrastruct.com/d2@latest` to install from source
|
So you can run `go install oss.terrastruct.com/d2@latest` to install from source
|
||||||
now.
|
now.
|
||||||
[#xxx](https://github.com/terrastruct/d2/pull/xxx)
|
[#290](https://github.com/terrastruct/d2/pull/290)
|
||||||
|
|
||||||
#### Bugfixes 🔴
|
#### Bugfixes 🔴
|
||||||
|
|
||||||
|
|
|
||||||
2
ci/sub
2
ci/sub
|
|
@ -1 +1 @@
|
||||||
Subproject commit 28fb67e3bf11d7df2be9ad57b67b78a1733a7f2d
|
Subproject commit 0dacc9c6cee5b8d901f22f57e9dc7f9acf640cbc
|
||||||
10
d2lib/d2.go
10
d2lib/d2.go
|
|
@ -22,7 +22,7 @@ type CompileOptions struct {
|
||||||
ThemeID int64
|
ThemeID int64
|
||||||
}
|
}
|
||||||
|
|
||||||
func Compile(ctx context.Context, input string, opts *CompileOptions) (*d2target.Diagram, error) {
|
func Compile(ctx context.Context, input string, opts *CompileOptions) (*d2target.Diagram, *d2graph.Graph, error) {
|
||||||
if opts == nil {
|
if opts == nil {
|
||||||
opts = &CompileOptions{}
|
opts = &CompileOptions{}
|
||||||
}
|
}
|
||||||
|
|
@ -31,12 +31,12 @@ func Compile(ctx context.Context, input string, opts *CompileOptions) (*d2target
|
||||||
UTF16: opts.UTF16,
|
UTF16: opts.UTF16,
|
||||||
})
|
})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
err = g.SetDimensions(opts.MeasuredTexts, opts.Ruler)
|
err = g.SetDimensions(opts.MeasuredTexts, opts.Ruler)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
if opts.Layout != nil {
|
if opts.Layout != nil {
|
||||||
|
|
@ -47,11 +47,11 @@ func Compile(ctx context.Context, input string, opts *CompileOptions) (*d2target
|
||||||
err = errors.New("no available layout")
|
err = errors.New("no available layout")
|
||||||
}
|
}
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
diagram, err := d2exporter.Export(ctx, g, opts.ThemeID)
|
diagram, err := d2exporter.Export(ctx, g, opts.ThemeID)
|
||||||
return diagram, err
|
return diagram, g, err
|
||||||
}
|
}
|
||||||
|
|
||||||
// See c.go
|
// See c.go
|
||||||
|
|
|
||||||
1
docs/examples/lib/1-d2lib/.gitignore
vendored
Normal file
1
docs/examples/lib/1-d2lib/.gitignore
vendored
Normal file
|
|
@ -0,0 +1 @@
|
||||||
|
out.svg
|
||||||
25
docs/examples/lib/1-d2lib/d2lib.go
Normal file
25
docs/examples/lib/1-d2lib/d2lib.go
Normal file
|
|
@ -0,0 +1,25 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"io/ioutil"
|
||||||
|
"path/filepath"
|
||||||
|
|
||||||
|
"oss.terrastruct.com/d2/d2layouts/d2dagrelayout"
|
||||||
|
"oss.terrastruct.com/d2/d2lib"
|
||||||
|
"oss.terrastruct.com/d2/d2renderers/d2svg"
|
||||||
|
"oss.terrastruct.com/d2/d2renderers/textmeasure"
|
||||||
|
"oss.terrastruct.com/d2/d2themes/d2themescatalog"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Remember to add if err != nil checks in production.
|
||||||
|
func main() {
|
||||||
|
ruler, _ := textmeasure.NewRuler()
|
||||||
|
diagram, _, _ := d2lib.Compile(context.Background(), "x -> y", &d2lib.CompileOptions{
|
||||||
|
Layout: d2dagrelayout.Layout,
|
||||||
|
Ruler: ruler,
|
||||||
|
ThemeID: d2themescatalog.GrapeSoda.ID,
|
||||||
|
})
|
||||||
|
out, _ := d2svg.Render(diagram)
|
||||||
|
_ = ioutil.WriteFile(filepath.Join("out.svg"), out, 0600)
|
||||||
|
}
|
||||||
9
docs/examples/lib/1-d2lib/d2lib_test.go
Normal file
9
docs/examples/lib/1-d2lib/d2lib_test.go
Normal file
|
|
@ -0,0 +1,9 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestMain_(t *testing.T) {
|
||||||
|
main()
|
||||||
|
}
|
||||||
36
docs/examples/lib/2-d2oracle/d2oracle.go
Normal file
36
docs/examples/lib/2-d2oracle/d2oracle.go
Normal file
|
|
@ -0,0 +1,36 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"fmt"
|
||||||
|
|
||||||
|
"oss.terrastruct.com/d2/d2format"
|
||||||
|
"oss.terrastruct.com/d2/d2layouts/d2dagrelayout"
|
||||||
|
"oss.terrastruct.com/d2/d2lib"
|
||||||
|
"oss.terrastruct.com/d2/d2oracle"
|
||||||
|
"oss.terrastruct.com/d2/d2renderers/textmeasure"
|
||||||
|
"oss.terrastruct.com/d2/d2themes/d2themescatalog"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Remember to add if err != nil checks in production.
|
||||||
|
func main() {
|
||||||
|
// From one.go
|
||||||
|
ruler, _ := textmeasure.NewRuler()
|
||||||
|
_, graph, _ := d2lib.Compile(context.Background(), "x -> y", &d2lib.CompileOptions{
|
||||||
|
Layout: d2dagrelayout.Layout,
|
||||||
|
Ruler: ruler,
|
||||||
|
ThemeID: d2themescatalog.GrapeSoda.ID,
|
||||||
|
})
|
||||||
|
|
||||||
|
// Create a shape with the ID, "meow"
|
||||||
|
graph, _, _ = d2oracle.Create(graph, "meow")
|
||||||
|
// Style the shape green
|
||||||
|
color := "green"
|
||||||
|
graph, _ = d2oracle.Set(graph, "meow.style.fill", nil, &color)
|
||||||
|
// Create a shape with the ID, "cat"
|
||||||
|
graph, _, _ = d2oracle.Create(graph, "cat")
|
||||||
|
// Move the shape "meow" inside the container "cat"
|
||||||
|
graph, _ = d2oracle.Move(graph, "meow", "cat.meow")
|
||||||
|
// Prints formatted D2 script
|
||||||
|
fmt.Print(d2format.Format(graph.AST))
|
||||||
|
}
|
||||||
9
docs/examples/lib/2-d2oracle/d2oracle_test.go
Normal file
9
docs/examples/lib/2-d2oracle/d2oracle_test.go
Normal file
|
|
@ -0,0 +1,9 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestMain_(t *testing.T) {
|
||||||
|
main()
|
||||||
|
}
|
||||||
1
docs/examples/lib/3-lowlevel/.gitignore
vendored
Normal file
1
docs/examples/lib/3-lowlevel/.gitignore
vendored
Normal file
|
|
@ -0,0 +1 @@
|
||||||
|
out.svg
|
||||||
26
docs/examples/lib/3-lowlevel/lowlevel.go
Normal file
26
docs/examples/lib/3-lowlevel/lowlevel.go
Normal file
|
|
@ -0,0 +1,26 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"io/ioutil"
|
||||||
|
"path/filepath"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"oss.terrastruct.com/d2/d2compiler"
|
||||||
|
"oss.terrastruct.com/d2/d2exporter"
|
||||||
|
"oss.terrastruct.com/d2/d2layouts/d2dagrelayout"
|
||||||
|
"oss.terrastruct.com/d2/d2renderers/d2svg"
|
||||||
|
"oss.terrastruct.com/d2/d2renderers/textmeasure"
|
||||||
|
"oss.terrastruct.com/d2/d2themes/d2themescatalog"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Remember to add if err != nil checks in production.
|
||||||
|
func main() {
|
||||||
|
graph, _ := d2compiler.Compile("", strings.NewReader("x -> y"), nil)
|
||||||
|
ruler, _ := textmeasure.NewRuler()
|
||||||
|
_ = graph.SetDimensions(nil, ruler)
|
||||||
|
_ = d2dagrelayout.Layout(context.Background(), graph)
|
||||||
|
diagram, _ := d2exporter.Export(context.Background(), graph, d2themescatalog.NeutralDefault.ID)
|
||||||
|
out, _ := d2svg.Render(diagram)
|
||||||
|
_ = ioutil.WriteFile(filepath.Join("out.svg"), out, 0600)
|
||||||
|
}
|
||||||
9
docs/examples/lib/3-lowlevel/lowlevel_test.go
Normal file
9
docs/examples/lib/3-lowlevel/lowlevel_test.go
Normal file
|
|
@ -0,0 +1,9 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestMain_(t *testing.T) {
|
||||||
|
main()
|
||||||
|
}
|
||||||
30
docs/examples/lib/README.md
Normal file
30
docs/examples/lib/README.md
Normal file
|
|
@ -0,0 +1,30 @@
|
||||||
|
# D2 library examples
|
||||||
|
|
||||||
|
We have a few examples in this directory on how to use the D2 library to turn D2 scripts
|
||||||
|
into rendered svg diagrams and more.
|
||||||
|
|
||||||
|
Each example is runnable though does not include error handling for readability.
|
||||||
|
|
||||||
|
### [./1-d2lib](./1-d2lib)
|
||||||
|
|
||||||
|
A minimal example showing you how to compile the diagram `x -> y` into an svg.
|
||||||
|
|
||||||
|
### [./2-d2oracle](./2-d2oracle)
|
||||||
|
|
||||||
|
D2 is built to be hackable -- the language has an API built on top of it to make edits
|
||||||
|
programmatically.
|
||||||
|
|
||||||
|
Modifying the previous example, this example demonstrates how
|
||||||
|
[d2oracle](../../../d2oracle) can be used to create a new shape, style it programatically
|
||||||
|
and then output the modified d2 script.
|
||||||
|
|
||||||
|
This makes it easy to build functionality on top of D2. Terrastruct uses the
|
||||||
|
[d2oracle](../../../d2oracle) API to implement editing of D2 from mouse actions in a
|
||||||
|
visual interface.
|
||||||
|
|
||||||
|
### [./3-lowlevel](./3-lowlevel)
|
||||||
|
|
||||||
|
`d2lib` from the first example is just a wrapper around the lower level APIs. They
|
||||||
|
can be used directly and this example demonstrates such usage.
|
||||||
|
|
||||||
|
This shouldn't be necessary for most usecases.
|
||||||
|
|
@ -19,7 +19,7 @@ import (
|
||||||
"oss.terrastruct.com/d2/d2graph"
|
"oss.terrastruct.com/d2/d2graph"
|
||||||
"oss.terrastruct.com/d2/d2layouts/d2dagrelayout"
|
"oss.terrastruct.com/d2/d2layouts/d2dagrelayout"
|
||||||
"oss.terrastruct.com/d2/d2layouts/d2elklayout"
|
"oss.terrastruct.com/d2/d2layouts/d2elklayout"
|
||||||
d2 "oss.terrastruct.com/d2/d2lib"
|
"oss.terrastruct.com/d2/d2lib"
|
||||||
"oss.terrastruct.com/d2/d2renderers/d2svg"
|
"oss.terrastruct.com/d2/d2renderers/d2svg"
|
||||||
"oss.terrastruct.com/d2/d2renderers/textmeasure"
|
"oss.terrastruct.com/d2/d2renderers/textmeasure"
|
||||||
"oss.terrastruct.com/d2/d2target"
|
"oss.terrastruct.com/d2/d2target"
|
||||||
|
|
@ -104,7 +104,7 @@ func run(t *testing.T, tc testCase) {
|
||||||
} else if layoutName == "elk" {
|
} else if layoutName == "elk" {
|
||||||
layout = d2elklayout.Layout
|
layout = d2elklayout.Layout
|
||||||
}
|
}
|
||||||
diagram, err := d2.Compile(ctx, tc.script, &d2.CompileOptions{
|
diagram, _, err := d2lib.Compile(ctx, tc.script, &d2lib.CompileOptions{
|
||||||
UTF16: true,
|
UTF16: true,
|
||||||
Ruler: ruler,
|
Ruler: ruler,
|
||||||
ThemeID: 0,
|
ThemeID: 0,
|
||||||
|
|
|
||||||
6
main.go
6
main.go
|
|
@ -15,7 +15,7 @@ import (
|
||||||
"go.uber.org/multierr"
|
"go.uber.org/multierr"
|
||||||
|
|
||||||
"oss.terrastruct.com/d2/d2layouts/d2sequence"
|
"oss.terrastruct.com/d2/d2layouts/d2sequence"
|
||||||
d2 "oss.terrastruct.com/d2/d2lib"
|
"oss.terrastruct.com/d2/d2lib"
|
||||||
"oss.terrastruct.com/d2/d2plugin"
|
"oss.terrastruct.com/d2/d2plugin"
|
||||||
"oss.terrastruct.com/d2/d2renderers/d2svg"
|
"oss.terrastruct.com/d2/d2renderers/d2svg"
|
||||||
"oss.terrastruct.com/d2/d2renderers/textmeasure"
|
"oss.terrastruct.com/d2/d2renderers/textmeasure"
|
||||||
|
|
@ -196,7 +196,7 @@ func compile(ctx context.Context, ms *xmain.State, plugin d2plugin.Plugin, theme
|
||||||
if os.Getenv("D2_SEQUENCE") == "1" {
|
if os.Getenv("D2_SEQUENCE") == "1" {
|
||||||
layout = d2sequence.Layout
|
layout = d2sequence.Layout
|
||||||
}
|
}
|
||||||
d, err := d2.Compile(ctx, string(input), &d2.CompileOptions{
|
diagram, _, err := d2lib.Compile(ctx, string(input), &d2lib.CompileOptions{
|
||||||
Layout: layout,
|
Layout: layout,
|
||||||
Ruler: ruler,
|
Ruler: ruler,
|
||||||
ThemeID: themeID,
|
ThemeID: themeID,
|
||||||
|
|
@ -205,7 +205,7 @@ func compile(ctx context.Context, ms *xmain.State, plugin d2plugin.Plugin, theme
|
||||||
return nil, false, err
|
return nil, false, err
|
||||||
}
|
}
|
||||||
|
|
||||||
svg, err := d2svg.Render(d)
|
svg, err := d2svg.Render(diagram)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, false, err
|
return nil, false, err
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue