Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
48 changes: 0 additions & 48 deletions .github/workflows/architecture.yml

This file was deleted.

11 changes: 9 additions & 2 deletions .golangci.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,9 @@ linters:
- G122 # filepath.Walk TOCTOU — acceptable for repo archiving
- G117 # secret field in marshaled struct — intentional (config file)
- G104 # unhandled errors — covered by errcheck with targeted exclusions
- G301 # directory permissions 0755 — intentional for static site output
- G306 # file write permissions 0644 — intentional for static site output
- G703 # path traversal — output paths come from user-supplied CLI flags
exclusions:
rules:
# Deferred and best-effort closes are idiomatic Go — errors not actionable.
Expand All @@ -48,9 +51,13 @@ linters:
# fmt.Fprintf/Fprintln to stdout/stderr — write errors are not actionable.
- text: 'Error return value of `fmt\.Fp?rint'
linters: [errcheck]
# Best-effort temp file cleanup.
- text: 'Error return value of `os\.Remove` is not checked'
# Best-effort temp file/dir cleanup.
- text: 'Error return value of `os\.Remove(All)?` is not checked'
linters: [errcheck]
# Ported packages from supermodeltools/arch-docs — style/complexity issues are
# acceptable in vendored/ported code; fixing them would cause needless upstream divergence.
- path: 'internal/archdocs/(graph2md|pssg)/'
linters: [gocritic, gocyclo, gosec, revive, ineffassign, staticcheck]
# Test files get more latitude.
- path: _test\.go
linters: [errcheck, gosec, gocritic]
Expand Down
57 changes: 57 additions & 0 deletions cmd/archdocs.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
package cmd

import (
"github.com/spf13/cobra"

"github.com/supermodeltools/cli/internal/archdocs"
"github.com/supermodeltools/cli/internal/config"
)

func init() {
var opts archdocs.Options

c := &cobra.Command{
Use: "arch-docs [path]",
Short: "Generate static architecture documentation for a repository",
Long: `Generate a static HTML site documenting the architecture of a codebase.

The command uploads the repository to the Supermodel API, converts the
returned code graph to markdown, and builds a browsable static site with
search, dependency graphs, taxonomy navigation, and SEO metadata.

The output directory can be served locally or deployed to any static host
(GitHub Pages, Vercel, Netlify, Cloudflare Pages, etc.).

Examples:
supermodel arch-docs
supermodel arch-docs ./my-project --output ./docs-site
supermodel arch-docs --repo owner/repo --base-url https://owner.github.io/repo
supermodel arch-docs --site-name "My App Docs" --output /var/www/html`,
Args: cobra.MaximumNArgs(1),
RunE: func(cmd *cobra.Command, args []string) error {
cfg, err := config.Load()
if err != nil {
return err
}
if err := cfg.RequireAPIKey(); err != nil {
return err
}
dir := "."
if len(args) > 0 {
dir = args[0]
}
return archdocs.Run(cmd.Context(), cfg, dir, opts)
},
}

c.Flags().StringVar(&opts.SiteName, "site-name", "", "display title for the generated site (default: \"<repo> Architecture Docs\")")
c.Flags().StringVar(&opts.BaseURL, "base-url", "", "canonical base URL where the site will be hosted (default: https://example.com)")
c.Flags().StringVar(&opts.Repo, "repo", "", "GitHub repo slug owner/repo used to build source links")
c.Flags().StringVarP(&opts.Output, "output", "o", "", "output directory for the generated site (default: ./arch-docs-output)")
c.Flags().StringVar(&opts.TemplatesDir, "templates-dir", "", "override bundled HTML/CSS/JS templates with a custom directory")
c.Flags().IntVar(&opts.MaxSourceFiles, "max-source-files", 3000, "maximum source files to include in analysis (0 = unlimited)")
c.Flags().IntVar(&opts.MaxEntities, "max-entities", 12000, "maximum entity pages to generate (0 = unlimited)")
c.Flags().BoolVar(&opts.Force, "force", false, "bypass cache and re-upload even if a cached result exists")

rootCmd.AddCommand(c)
}
11 changes: 11 additions & 0 deletions internal/api/client.go
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,17 @@ func (c *Client) Analyze(ctx context.Context, zipPath, idempotencyKey string) (*
return &result.Graph, nil
}

// AnalyzeRaw uploads a repository ZIP and runs the full analysis pipeline,
// returning the raw result JSON from the completed job. Use this when you need
// the full response payload (e.g. for graph2md / arch-docs generation).
func (c *Client) AnalyzeRaw(ctx context.Context, zipPath, idempotencyKey string) (json.RawMessage, error) {
job, err := c.pollUntilComplete(ctx, zipPath, idempotencyKey)
if err != nil {
return nil, err
}
return job.Result, nil
}

// AnalyzeDomains uploads a repository ZIP and runs the full analysis pipeline,
// returning the complete SupermodelIR response (domains, summary, metadata, graph).
// Use this instead of Analyze when you need high-level domain information.
Expand Down
Loading
Loading