Skip to content

Commit

Permalink
new implementation
Browse files Browse the repository at this point in the history
  • Loading branch information
alixander committed Jul 19, 2023
1 parent ab81df7 commit 3d0422f
Show file tree
Hide file tree
Showing 8 changed files with 136 additions and 145 deletions.
174 changes: 67 additions & 107 deletions d2cli/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import (
"oss.terrastruct.com/util-go/go2"
"oss.terrastruct.com/util-go/xmain"

"oss.terrastruct.com/d2/d2graph"
"oss.terrastruct.com/d2/d2lib"
"oss.terrastruct.com/d2/d2parser"
"oss.terrastruct.com/d2/d2plugin"
Expand Down Expand Up @@ -227,18 +228,33 @@ func Run(ctx context.Context, ms *xmain.State) (err error) {
ms.Log.Debug.Printf("using theme %s (ID: %d)", match.Name, *themeFlag)

// If not set by user, nil, so that diagramConfig can take precedent
if *themeFlag == 0 {
flagSet := make(map[string]struct{})
ms.Opts.Flags.Visit(func(f *pflag.Flag) {
flagSet[f.Name] = struct{}{}
})
if ms.Env.Getenv("D2_THEME") == "" {
if _, ok := flagSet["theme"]; !ok {
themeFlag = nil
}
flagSet := make(map[string]struct{})
ms.Opts.Flags.Visit(func(f *pflag.Flag) {
flagSet[f.Name] = struct{}{}
})
if ms.Env.Getenv("D2_THEME") == "" {
if _, ok := flagSet["theme"]; !ok {
themeFlag = nil
}
}
if ms.Env.Getenv("D2_LAYOUT") == "" {
if _, ok := flagSet["layout"]; !ok {
layoutFlag = nil
}
}
if ms.Env.Getenv("D2_SKETCH") == "" {
if _, ok := flagSet["sketch"]; !ok {
sketchFlag = nil
}
}

if ms.Env.Getenv("D2_PAD") == "" {
if _, ok := flagSet["pad"]; !ok {
padFlag = nil
}
}

// TODO
if *darkThemeFlag == -1 {
darkThemeFlag = nil // TODO this is a temporary solution: https://github.com/terrastruct/util-go/issues/7
}
Expand Down Expand Up @@ -275,9 +291,9 @@ func Run(ctx context.Context, ms *xmain.State) (err error) {
}

renderOpts := d2svg.RenderOpts{
Pad: int(*padFlag),
Sketch: *sketchFlag,
Center: *centerFlag,
Pad: padFlag,
Sketch: sketchFlag,
Center: centerFlag,
ThemeID: themeFlag,
DarkThemeID: darkThemeFlag,
Scale: scale,
Expand All @@ -289,7 +305,7 @@ func Run(ctx context.Context, ms *xmain.State) (err error) {
}
w, err := newWatcher(ctx, ms, watcherOpts{
plugins: plugins,
layout: *layoutFlag,
layout: layoutFlag,
renderOpts: renderOpts,
animateInterval: *animateIntervalFlag,
host: *hostFlag,
Expand All @@ -310,7 +326,7 @@ func Run(ctx context.Context, ms *xmain.State) (err error) {
ctx, cancel := timelib.WithTimeout(ctx, time.Minute*2)
defer cancel()

_, written, err := compile(ctx, ms, plugins, *layoutFlag, renderOpts, fontFamily, *animateIntervalFlag, inputPath, outputPath, *bundleFlag, *forceAppendixFlag, pw.Page)
_, written, err := compile(ctx, ms, plugins, layoutFlag, renderOpts, fontFamily, *animateIntervalFlag, inputPath, outputPath, *bundleFlag, *forceAppendixFlag, pw.Page)
if err != nil {
if written {
return fmt.Errorf("failed to fully compile (partial render written): %w", err)
Expand All @@ -320,7 +336,26 @@ func Run(ctx context.Context, ms *xmain.State) (err error) {
return nil
}

func compile(ctx context.Context, ms *xmain.State, plugins []d2plugin.Plugin, layout string, renderOpts d2svg.RenderOpts, fontFamily *d2fonts.FontFamily, animateInterval int64, inputPath, outputPath string, bundle, forceAppendix bool, page playwright.Page) (_ []byte, written bool, _ error) {
func LayoutResolver(ctx context.Context, ms *xmain.State, plugins []d2plugin.Plugin) func(engine string) (d2graph.LayoutGraph, error) {
return func(engine string) (d2graph.LayoutGraph, error) {
plugin, err := d2plugin.FindPlugin(ctx, plugins, engine)
if err != nil {
if errors.Is(err, exec.ErrNotFound) {
return nil, layoutNotFound(ctx, plugins, engine)
}
return nil, err
}

err = d2plugin.HydratePluginOpts(ctx, ms, plugin)
if err != nil {
return nil, err
}

return plugin.Layout, nil
}
}

func compile(ctx context.Context, ms *xmain.State, plugins []d2plugin.Plugin, layout *string, renderOpts d2svg.RenderOpts, fontFamily *d2fonts.FontFamily, animateInterval int64, inputPath, outputPath string, bundle, forceAppendix bool, page playwright.Page) (_ []byte, written bool, _ error) {
start := time.Now()
input, err := ms.ReadPath(inputPath)
if err != nil {
Expand All @@ -333,12 +368,14 @@ func compile(ctx context.Context, ms *xmain.State, plugins []d2plugin.Plugin, la
}

opts := &d2lib.CompileOptions{
Ruler: ruler,
ThemeID: renderOpts.ThemeID,
FontFamily: fontFamily,
InputPath: inputPath,
}
if renderOpts.Sketch {
Ruler: ruler,
ThemeID: renderOpts.ThemeID,
FontFamily: fontFamily,
InputPath: inputPath,
LayoutResolver: LayoutResolver(ctx, ms, plugins),
Layout: layout,
}
if renderOpts.Sketch != nil && *renderOpts.Sketch {
opts.FontFamily = go2.Pointer(d2fonts.HandDrawn)
}

Expand All @@ -347,32 +384,20 @@ func compile(ctx context.Context, ms *xmain.State, plugins []d2plugin.Plugin, la
}, time.Second*5)
defer cancel()

g, diagramConfig, err := d2lib.Compile(ctx, string(input), opts)
diagram, g, err := d2lib.Compile(ctx, string(input), opts, &renderOpts)
if err != nil {
return nil, false, err
}
cancel()

diagramConfigLayout := applyDiagramConfig(ctx, ms, &renderOpts, diagramConfig)
if diagramConfigLayout != "" {
layout = diagramConfigLayout
}
plugin, _ := d2plugin.FindPlugin(ctx, plugins, *opts.Layout)

if renderOpts.ThemeID == nil {
renderOpts.ThemeID = &d2themescatalog.NeutralDefault.ID
}

plugin, err := d2plugin.FindPlugin(ctx, plugins, layout)
if err != nil {
if errors.Is(err, exec.ErrNotFound) {
return nil, false, layoutNotFound(ctx, plugins, layout)
if animateInterval > 0 {
masterID, err := diagram.HashID()
if err != nil {
return nil, false, err
}
return nil, false, err
}

err = d2plugin.HydratePluginOpts(ctx, ms, plugin)
if err != nil {
return nil, false, err
renderOpts.MasterID = masterID
}

pinfo, err := plugin.Info(ctx)
Expand All @@ -383,21 +408,7 @@ func compile(ctx context.Context, ms *xmain.State, plugins []d2plugin.Plugin, la
if pinfo.Type == "binary" {
plocation = fmt.Sprintf("executable plugin at %s", humanPath(pinfo.Path))
}
ms.Log.Debug.Printf("using layout plugin %s (%s)", layout, plocation)
opts.Layout = plugin.Layout

diagram, err := d2lib.Export(ctx, g, opts)
if err != nil {
return nil, false, err
}

if animateInterval > 0 {
masterID, err := diagram.HashID()
if err != nil {
return nil, false, err
}
renderOpts.MasterID = masterID
}
ms.Log.Debug.Printf("using layout plugin %s (%s)", *opts.Layout, plocation)

pluginInfo, err := plugin.Info(ctx)
if err != nil {
Expand Down Expand Up @@ -832,7 +843,7 @@ func renderPDF(ctx context.Context, ms *xmain.State, plugin d2plugin.Plugin, opt
if err != nil {
return svg, err
}
err = doc.AddPDFPage(pngImg, boardPath, *opts.ThemeID, rootFill, diagram.Shapes, int64(opts.Pad), viewboxX, viewboxY, pageMap)
err = doc.AddPDFPage(pngImg, boardPath, *opts.ThemeID, rootFill, diagram.Shapes, *opts.Pad, viewboxX, viewboxY, pageMap)
if err != nil {
return svg, err
}
Expand Down Expand Up @@ -1195,54 +1206,3 @@ func renderPNGsForGIF(ctx context.Context, ms *xmain.State, plugin d2plugin.Plug

return svg, pngs, nil
}

// TODO this comment
// Apply diagram config, but secondary to flag and env vars
func applyDiagramConfig(ctx context.Context, ms *xmain.State, opts *d2svg.RenderOpts, config *d2target.Config) (layout string) {
flagSet := make(map[string]struct{})
ms.Opts.Flags.Visit(func(f *pflag.Flag) {
flagSet[f.Name] = struct{}{}
})

if config.Sketch != nil {
if ms.Env.Getenv("D2_SKETCH") == "" {
if _, ok := flagSet["sketch"]; !ok {
opts.Sketch = *config.Sketch
}
}
}

if config.ThemeID != nil {
if ms.Env.Getenv("D2_THEME") == "" {
if _, ok := flagSet["theme"]; !ok {
opts.ThemeID = config.ThemeID
}
}
}

if config.DarkThemeID != nil {
if ms.Env.Getenv("D2_DARK_THEME") == "" {
if _, ok := flagSet["dark-theme"]; !ok {
opts.DarkThemeID = config.DarkThemeID
}
}
}

if config.Pad != nil {
if ms.Env.Getenv("D2_PAD") == "" {
if _, ok := flagSet["pad"]; !ok {
opts.Pad = *config.Pad
}
}
}

if config.LayoutEngine != nil {
if ms.Env.Getenv("D2_LAYOUT") == "" {
if _, ok := flagSet["layout"]; !ok {
layout = *config.LayoutEngine
}
}
}

return
}
2 changes: 1 addition & 1 deletion d2cli/watch.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ var devMode = false
var staticFS embed.FS

type watcherOpts struct {
layout string
layout *string
plugins []d2plugin.Plugin
renderOpts d2svg.RenderOpts
animateInterval int64
Expand Down
2 changes: 1 addition & 1 deletion d2compiler/compile.go
Original file line number Diff line number Diff line change
Expand Up @@ -1318,7 +1318,7 @@ func compileConfig(ir *d2ir.Map) *d2target.Config {
f = configMap.GetField("pad")
if f != nil {
val, _ := strconv.Atoi(f.Primary().Value.ScalarString())
config.Pad = go2.Pointer(val)
config.Pad = go2.Pointer(int64(val))
}

f = configMap.GetField("layout-engine")
Expand Down
1 change: 1 addition & 0 deletions d2ir/compile.go
Original file line number Diff line number Diff line change
Expand Up @@ -161,6 +161,7 @@ func (c *compiler) validateConfigs(configs *Field) {
c.errorf(f.LastRef().AST(), `"%s" needs a map`, f.Name)
continue
}
case "layout-engine":
default:
c.errorf(f.LastRef().AST(), `"%s" is not a valid config`, f.Name)
}
Expand Down
Loading

0 comments on commit 3d0422f

Please sign in to comment.