format

package
v1.0.3 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Aug 31, 2026 License: MIT Imports: 11 Imported by: 0

Documentation

Overview

Package format holds what the commands share when rendering API results: the --format enum they render in, and the text helpers themselves — storage-XHTML to Markdown conversion, search highlight-marker stripping and indentation.

Nothing here rewrites a body. A page body that will be written back is read from and written to a file untouched, so that path stays byte-lossless; the conversions in this package produce output for reading only, and Macros -- the one thing here an edit does consult — reports where a macro's parameters sit and leaves the writing to its caller.

ToMarkdown serves both readers of a storage body: `read --markdown`, whose output carries no sidecar and cannot be updated, and comment bodies, which arrive as storage XHTML because the comment endpoints refuse body-format=view.

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func ElementEnds

func ElementEnds(storage, localID string) []int

ElementEnds reports where each element carrying the given local-id ends: the byte just past its end tag, which is where a sibling inserted after it starts. The offsets index the string that was passed in, in document order.

Confluence stamps local-id on block elements (<p>, headings, …) and ac:local-id on macros. Those are the same attribute under different prefixes, and the attribute is read by local name — the way every other attribute in this package is read — so either one is a usable anchor.

Every match is reported rather than the first: a body should not carry the same id twice, but acting on the first of two would insert somewhere the caller never named. Deciding what to do with none or several is the caller's business, the way it is for Macros.

func Indent

func Indent(text, prefix string) string

Indent prefixes every line of text, leaving blank lines unpadded so no trailing whitespace is emitted.

func StripHighlightMarkers

func StripHighlightMarkers(s string) string

StripHighlightMarkers removes the markers Confluence search wraps around matched terms and decodes the HTML entities that come with them. A value without markers passes through unchanged, so this is safe to apply even if the server stops adding them.

Types

type Format

type Format string

Format is the output format a command renders its result in. It implements pflag.Value, so an unknown --format is rejected while cobra parses the flags: before PreRunE and RunE both, which leaves no hook a command could take over and no way to reach a command body with an unvalidated value.

const (
	Markdown Format = "md"
	JSON     Format = "json"
)

The two accepted --format values.

func (*Format) Set

func (f *Format) Set(s string) error

Set implements pflag.Value. It assigns only after validating, so a typo leaves the receiver — and with it the default the flag was registered with — untouched.

func (Format) String

func (f Format) String() string

func (Format) Type

func (Format) Type() string

Type names the value cobra prints in the --format help line. It reports "string" rather than "format" because that line is part of the agent-facing contract kept in sync with README.md and skills/cflio/SKILL.md.

func (Format) Validate

func (f Format) Validate() error

Validate rejects a Format that is not one of the accepted values. Set is not the only way to build a Format — a conversion from an arbitrary string still type-checks — so the callers that branch on one keep this guard rather than trusting the type.

type Macro

type Macro struct {
	// Name is the ac:name attribute, e.g. "plantumlcloud".
	Name string
	// LocalID is the ac:local-id attribute, empty when the element carries
	// none. It is the stable identifier across editor saves — Confluence
	// reissues ac:macro-id but keeps this — so it is what a caller selects a
	// macro by.
	LocalID string
	// Params are the macro's direct ac:parameter children, in document order.
	Params []MacroParam
}

Macro is one ac:structured-macro found in a storage body.

func Macros

func Macros(storage string) []Macro

Macros scans a storage body for its macros, in document order, and reports where each parameter's text sits so a caller can rewrite one in place.

It only reads: the returned offsets index the string that was passed in, and splicing a new value into one is the caller's business. That is what keeps this package out of the edit round-trip while still being the one place that knows how to parse a storage body — the scan has to configure its decoder exactly as the Markdown conversion does, and a second copy of that configuration elsewhere would drift.

func (Macro) Param

func (m Macro) Param(name string) (MacroParam, bool)

Param returns the parameter with the given name.

type MacroParam

type MacroParam struct {
	Name       string
	Value      string
	Start, End int
	// Empty marks a parameter written as a self-closing tag. Such an element
	// has no content, so Start and End meet just past its "/>", outside the
	// parameter — a caller must not write there.
	Empty bool
}

MacroParam is one ac:parameter, with both what it says and where it says it.

Value is the text the parameter carries, entity references resolved and surrounding whitespace trimmed — the same thing the Markdown converter reads. Start and End bound that text in the storage string Macros was given, as raw bytes: no entity is resolved there, and no whitespace is trimmed off. The two therefore differ for any value written with an entity or padded with whitespace, which is why replacing a range is only safe for a value whose text and bytes are the same thing — a base64 payload or a number.

type Options

type Options struct {
	// UserNames maps an Atlassian account ID to a display name.
	UserNames map[string]string
	// PageURLs maps a link target to the page's URL.
	PageURLs map[PageRef]string
	// AttachmentPaths maps an attachment's filename to the destination an
	// image of it links to. It holds what the caller wants written into the
	// link, which is not necessarily the path it wrote the file to: the
	// caller builds a link out of forward slashes, and on Windows the file
	// went to a path built out of backslashes.
	AttachmentPaths map[string]string
}

Options carries the reference resolution ToMarkdown cannot do itself. The converter is a pure function, so looking a name or a URL up — which needs the API — happens in the command layer and arrives here as data. A zero Options is valid: every reference falls back to what the body already carries.

type PageRef

type PageRef struct {
	SpaceKey string
	Title    string
}

PageRef names a page the way storage links to one: by space key and title, with no page ID anywhere in the body.

type Refs

type Refs struct {
	// AccountIDs are the ri:user targets.
	AccountIDs []string
	// Pages are the ri:page targets. SpaceKey is empty for a link to a page
	// in the same space, which is how storage writes one — and that empty key
	// is what Options.PageURLs has to be keyed by for the lookup to hit.
	Pages []PageRef
	// Attachments are the filenames the page's own images are sourced from.
	// A filename is all storage carries, and it is also what the attachment
	// listing identifies a file by, so it is what Options.AttachmentPaths is
	// keyed by too.
	Attachments []string
}

Refs are the references a body makes that ToMarkdown cannot render without an Options filled in from the API. Every slice is deduplicated and sorted, so the requests a caller builds from them are deterministic.

func References

func References(storage string) Refs

References collects what a caller has to resolve for ToMarkdown to render names, URLs and image paths instead of identifiers. It walks for the same targets link and image render, through the same accessors; the kinds worth resolving are listed in collectTarget and imageAttachment, which those two renderers have to be kept in step with.

Parsing the body twice — once here, once in ToMarkdown — is the price of keeping the converter a pure function. Returning the references from the conversion instead would cost the same parse plus a discarded render, since the resolution has to be in hand before the rendering that uses it.

type Result

type Result struct {
	Markdown string
	// Unsupported names the macros and extensions that became placeholders,
	// deduplicated and sorted; UnsupportedCount counts every occurrence. A
	// reader decides from these whether the rendering can be trusted, without
	// having to read the whole file first.
	Unsupported      []string
	UnsupportedCount int
}

Result is a conversion and what it could not represent.

func ToMarkdown

func ToMarkdown(storage string, opts Options) Result

ToMarkdown converts a storage-format body to Markdown for reading. It never fails: unknown input degrades in structure, never in content, so an element this converter has never seen still yields the text inside it.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL