layout

package
v0.6.25 Latest Latest
Warning

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

Go to latest
Published: Dec 8, 2025 License: AGPL-3.0 Imports: 22 Imported by: 0

Documentation

Overview

Copyright (C) Kumo inc. and its affiliates. Author: Jeff.li lijippy@163.com All rights reserved. This program is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.

This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more details.

You should have received a copy of the GNU Affero General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.

Index

Constants

View Source
const (
	OfficalMirror    = "https://github.com/kumose/mirror.git"
	OfficalSshMirror = "git@github.com:kumose/mirror.git"
)
View Source
const DefaultComponentReadmeContent = `` /* 585-byte string literal not displayed */
View Source
const DefaultKeep = `` /* 1957-byte string literal not displayed */
View Source
const DefaultLicenseContent = `` /* 700-byte string literal not displayed */

Default license content (matches the project's GNU Affero General Public License)

View Source
const DefaultReadmeContent = `` /* 1393-byte string literal not displayed */

Default README.md content

View Source
const DefaultVersionsReadmeContent = `` /* 956-byte string literal not displayed */

Variables

This section is empty.

Functions

func CheckComponentName

func CheckComponentName(name string) bool

CheckComponentName validates if a component name is legal and normalizes it (internal use for validation) Validation Rules: 1. First character must be a letter (a-z, A-Z) or digit (0-9) 2. Subsequent characters can be letters (a-z, A-Z), digits (0-9), or underscores (_) 3. Name cannot be empty, contain hyphens (-), or other special characters 4. Name cannot start with an underscore Note: The function only validates, not modifies the input; normalization (to lowercase) should be done separately Return: true if valid, false otherwise

func CommitChange

func CommitChange(mssage, user, email string) error

func CommitChangeAmend

func CommitChangeAmend(mssage, user, email string) error

func EnableGitLfs

func EnableGitLfs(dstDir string) error

EnableGitLfs creates/updates the .gitattributes file in the target directory to track all common archive/binary formats with Git LFS, while excluding text-based files (JSON, shell scripts, etc.) from LFS. dstDir: Target directory to place .gitattributes (typically repo root or component root) Returns error if directory creation or file write fails

func HeadHash

func HeadHash() (string, error)

func InitEmptyMirror

func InitEmptyMirror(dst, branch string) error

InitEmptyMirror initializes an empty component mirror with the standard directory structure dst: Root directory of the new mirror (will be created if it doesn't exist) Returns the initialized ComponentsLayout or error if any step fails

func InitMirrorWithTargetBranch

func InitMirrorWithTargetBranch(localDir, targetBranch string) error

initMirrorWithTargetBranch initializes mirror with specified target branch, bypassing go-git's hardcoded master

func IsClean

func IsClean() bool

func IsCleanWriteAble

func IsCleanWriteAble() (bool, error)

func IsWriteAble

func IsWriteAble() bool

func LoadIndex

func LoadIndex() error

func LoadMirror

func LoadMirror() error

func MirrorConfigPath

func MirrorConfigPath() string

func MirrorIndexPath

func MirrorIndexPath() string

func MirrorLocalPath

func MirrorLocalPath() string

func MrInit

func MrInit() error

func OfficalLocalPath

func OfficalLocalPath() string

func OfficalRemote

func OfficalRemote() string

func OfficalSshRemote

func OfficalSshRemote() string

func ResetMirror

func ResetMirror(dst, branch string) error

ResetMirror resets an existing mirror to empty initial state (clears history/files, keeps Git auth info

func RollbackCommit

func RollbackCommit(err error) error

RollbackCommit rolls back the repository to the base state (recorded in MirrorCtx.Hash) before the publish process Returns the original error with rollback status to ensure the caller is aware of the complete state

func SaveIndex

func SaveIndex() error

func SetConfig

func SetConfig(local, remote string) error

func TreeHash

func TreeHash(component string) (string, error)

func UncommitFiles

func UncommitFiles() ([]string, error)

UncommitFiles returns a list of files that have been modified but not committed

func UntrackedFiles

func UntrackedFiles() ([]string, error)

UncommitFiles returns a list of files that have been modified but not committed

Types

type BaselineComponent

type BaselineComponent struct {
	Baseline string `json:"baseline"` // Baseline version of the component (string format for flexibility)
	Channel  string `json:"channel"`  // Channel of the component (stable/nightly/beta)
}

BaselineComponent represents the baseline configuration for a single component

type BaselineConfig

type BaselineConfig struct {
	Version   *Serm                        `json:"version"`   // Baseline config version (semantic versioning via Serm)
	Timestamp time.Time                    `json:"timestamp"` // Last modification time (only updated on content change)
	Defaults  map[string]BaselineComponent `json:"defaults"`  // Component baseline mappings (key: component name)
}

BaselineConfig is the internal data structure for baseline (used by BaselineManager)

type BaselineManager

type BaselineManager struct {
	// contains filtered or unexported fields
}

BaselineManager is the core class for baseline management Encapsulates all baseline-related data and operations (strict versioning with Serm)

func NewBaselineManager

func NewBaselineManager() *BaselineManager

NewBaselineManager creates a new BaselineManager instance Initializes with default version 1.0.0 (via Serm) and empty component mappings

func (*BaselineManager) AddComponent

func (m *BaselineManager) AddComponent(name string, comp BaselineComponent, vt VersionType) error

AddComponent adds a new component to the baseline (strict uniqueness check) Mandatory version increment via Serm: Major/Minor/Patch (no way to skip)

func (*BaselineManager) CompareVersion

func (m *BaselineManager) CompareVersion(targetVersion string) int

CompareVersion compares current baseline version with a target version string Returns 1 (current newer), 0 (equal), -1 (current older)

func (*BaselineManager) Config

func (m *BaselineManager) Config() *BaselineConfig

func (*BaselineManager) DeleteComponent

func (m *BaselineManager) DeleteComponent(name string, vt VersionType) (bool, error)

DeleteComponent deletes an existing component (strict existence check) Mandatory version increment via Serm: Major/Minor/Patch (no way to skip) Returns (true, nil) on success; (false, error) if component not found

func (*BaselineManager) GetComponent

func (m *BaselineManager) GetComponent(name string) (BaselineComponent, bool)

GetComponent retrieves a component's configuration by name (read-only) Returns (component, true) if found; (empty struct, false) otherwise

func (*BaselineManager) GetCurrentVersion

func (m *BaselineManager) GetCurrentVersion() string

GetCurrentVersion returns the current baseline config version (as string, read-only)

func (*BaselineManager) GetLastModified

func (m *BaselineManager) GetLastModified() time.Time

GetLastModified returns the timestamp of the last content change (read-only)

func (*BaselineManager) ListComponents

func (m *BaselineManager) ListComponents() []string

ListComponents returns a sorted list of all component names (read-only)

func (*BaselineManager) Load

func (m *BaselineManager) Load(filePath string) error

Load loads baseline configuration from a JSON file into the manager Preserves the original version (Serm) and timestamp (no automatic increment)

func (*BaselineManager) Save

func (m *BaselineManager) Save(filePath string) error

Save serializes the current baseline configuration to a JSON file Sorts components alphabetically for readability; uses Serm's String() for version format

func (*BaselineManager) UpdateComponent

func (m *BaselineManager) UpdateComponent(name string, updatedComp BaselineComponent, vt VersionType) error

UpdateComponent updates an existing component (strict existence check) Mandatory version increment via Serm: Major/Minor/Patch (no way to skip)

type ComponentVersion

type ComponentVersion struct {
	GitTree   string    `json:"git-tree"`  // Git commit hash (populated after successful pre-operation)
	Version   string    `json:"version"`   // Component version (supports parallel versioning)
	Channel   string    `json:"channel"`   // Release channel (e.g., stable, beta, alpha)
	Timestamp time.Time `json:"timestamp"` // Release timestamp (populated after successful pre-operation)
}

ComponentVersion represents a single version entry of a component

func (*ComponentVersion) MarshalJSON

func (v *ComponentVersion) MarshalJSON() ([]byte, error)

-------------------------- JSON Serialization/Deserialization -------------------------- MarshalJSON customizes JSON serialization for ComponentVersion Converts Timestamp to RFC3339 string for consistent cross-system compatibility

func (*ComponentVersion) UnmarshalJSON

func (v *ComponentVersion) UnmarshalJSON(data []byte) error

UnmarshalJSON customizes JSON deserialization for ComponentVersion Parses RFC3339 timestamp string back to time.Time

type ComponentVersionList

type ComponentVersionList struct {
	Versions []ComponentVersion `json:"versions"` // Collection of all component versions
}

ComponentVersionList is the root structure of the version JSON file

func (*ComponentVersionList) Save

func (c *ComponentVersionList) Save(filePath string) error

SaveIndex serializes IndexConfig to formatted JSON and writes to file Only writes data (preserves existing Timestamp if no content change)

type ComponentVersionManager

type ComponentVersionManager struct {
	// contains filtered or unexported fields
}

ComponentVersionManager is the core manager for component version records Key constraint: Append new records ONLY after all pre-operations are successfully completed

func NewComponentVersionManager

func NewComponentVersionManager(versionFilePath string) *ComponentVersionManager

NewComponentVersionManager creates a new instance of ComponentVersionManager

func (*ComponentVersionManager) AppendNewRecord

func (m *ComponentVersionManager) AppendNewRecord(newRecord ComponentVersion) error

AppendNewRecord adds a new version record to the file (ONLY after pre-operations succeed) Enforces uniqueness: Combines Version + GitTree to avoid duplicate entries (Supports parallel versions: same Version with different GitTree is allowed)

func (*ComponentVersionManager) CheckExists

func (m *ComponentVersionManager) CheckExists(version, gitTree string) (bool, error)

CheckExists verifies if a version or git-tree already exists (for pre-operation validation) Returns true if either the version or git-tree is found in existing records

func (*ComponentVersionManager) Get added in v0.6.25

func (m *ComponentVersionManager) Get(version, gitTree string) (*ComponentVersion, error)

func (*ComponentVersionManager) GetAllRecords

func (m *ComponentVersionManager) GetAllRecords() ([]ComponentVersion, error)

GetAllRecords returns all version records sorted by timestamp (newest first) Defensive sort ensures consistent order even if file was modified externally

func (*ComponentVersionManager) Load

Load retrieves the existing version list from the JSON file Returns an empty list if the file doesn't exist (will be created on first append)

type ComponentsItem

type ComponentsItem struct {
	Name        string `json:"name"`        // Unique component identifier (primary key, non-duplicable)
	Owner       string `json:"owner"`       // Component owner (individual or team name)
	Description string `json:"description"` // Brief explanation of component's functionality
	Email       string `json:"email"`       // Owner's contact email for maintenance
	Source      string `json:"source"`      // URL of source code repository (e.g., GitHub)
	Home        string `json:"home"`        // Component's official homepage URL
	Docs        string `json:"docs"`        // URL of user/documentation guide
	Hide        bool   `json:"hide"`        // Whether to hide the component from public list
	Deprecate   bool   `json:"deprecate"`   // Whether the component is deprecated (no longer maintained)
}

ComponentsItem represents a single component entry in the index configuration Maps to each object in the "components" array of the JSON file

func LoadComponentFile

func LoadComponentFile(filePath string) (*ComponentsItem, error)

type ComponentsLayout

type ComponentsLayout struct {
	RootDir       string // Root directory of the mirror
	ComponentsDir string // Path to components directory (RootDir/components)
	VersionsDir   string // Path to versions directory (RootDir/versions)
	BaselinePath  string // Path to baseline.json (RootDir/baseline.json)
	IndexPath     string // Path to index.json (RootDir/index.json)
	LicensePath   string // Path to LICENSE (RootDir/LICENSE)
	ReadmePath    string // Path to README.md (RootDir/README.md)
}

ComponentsLayout defines the standard mirror directory structure configuration Follows the layout: ├── baseline.json (Baseline configuration for mirror) ├── components/ (Flat component directories with binary/manifest files) ├── index.json (Root index of all components and versions) ├── LICENSE (License file, same as the project license) ├── README.md (Mirror usage documentation) ├── versions/ (Version index directory, grouped by component name prefix) │ └── [prefix]/ (Component name prefix group, e.g., "s-" for server-* components) │ └── [component].json (Per-component version details)

func InitEmptyLayout

func InitEmptyLayout(dst string) (*ComponentsLayout, error)

InitEmptyMirror initializes an empty component mirror with the standard directory structure dst: Root directory of the new mirror (will be created if it doesn't exist) Returns the initialized ComponentsLayout or error if any step fails

func NewComponentsLayout

func NewComponentsLayout(dst string) *ComponentsLayout

func (*ComponentsLayout) ComponentVersionPath

func (c *ComponentsLayout) ComponentVersionPath(name string) (string, error)

ComponentVersionPath generates the path to the component's version.json file Rule: 1. Take the first character of the component name (name is assumed legal: only letter/number) 2. Convert the first character to lowercase (if it's a letter) 3. Path format: root/[firstChar]-/[name].json Example: - root="/components", name="Axxx" → "/components/a-/axxx.json" - root="/components", name="123Plugin" → "/components/1-/123plugin.json" - root="/components", name="Zebra" → "/components/z-/zebra.json"

type IndexConfig

type IndexConfig struct {
	Timestamp  time.Time        `json:"timestamp"`  // Last content modification time (local timezone, RFC3339 format)
	Components []ComponentsItem `json:"components"` // Collection of all components in the index
}

IndexConfig is the root structure of the index JSON file Contains global metadata and list of all registered components

func LoadIndexFile

func LoadIndexFile(filePath string) (*IndexConfig, error)

LoadIndexFile reads and parses index configuration from a JSON file Returns pointer to IndexConfig on success, error on failure (file not found, invalid JSON, etc.)

func (*IndexConfig) AddComponent

func (c *IndexConfig) AddComponent(item ComponentsItem) error

AddComponent appends a new component to the index Returns error if component name already exists (name is unique key) Updates Timestamp automatically on success

func (*IndexConfig) BatchSetComponentDeprecate

func (c *IndexConfig) BatchSetComponentDeprecate(names []string, deprecate bool) (int, []string, error)

BatchSetComponentDeprecate updates deprecate status for multiple components in one call names: Slice of target component names deprecate: New deprecate status to apply (true = deprecated, false = active) Returns (success count, failed component names, error) - error only if internal logic fails

func (*IndexConfig) BatchSetComponentHide

func (c *IndexConfig) BatchSetComponentHide(names []string, hide bool) (int, []string, error)

BatchSetComponentHide updates hide status for multiple components in one call names: Slice of target component names hide: New hide status to apply (true = hide, false = show) Returns (success count, failed component names, error) - error only if internal logic fails

func (*IndexConfig) DeleteComponent

func (c *IndexConfig) DeleteComponent(name string) error

DeleteComponent removes a component from the index by name Returns error if component does not exist Updates Timestamp automatically on success

func (*IndexConfig) GetComponent

func (c *IndexConfig) GetComponent(name string) *ComponentsItem

GetComponent retrieves a component by name Returns pointer to ComponentsItem if found, nil otherwise Returns a copy to prevent unintended modification of internal state

func (*IndexConfig) GetComponentRef added in v0.6.25

func (c *IndexConfig) GetComponentRef(name string) *ComponentsItem

GetComponent retrieves a component by name Returns pointer to ComponentsItem if found, nil otherwise Returns a copy to prevent unintended modification of internal state

func (*IndexConfig) GetComponentStatus

func (c *IndexConfig) GetComponentStatus(name string) (bool, bool, error)

GetComponentStatus returns the hide and deprecate status of a component Returns (hide status, deprecate status, error) - error if component not found

func (*IndexConfig) ListComponents

func (c *IndexConfig) ListComponents() []ComponentsItem

ListComponents returns a copy of all components in the index Prevents external code from modifying the internal component slice directly

func (*IndexConfig) ListDeprecatedComponents

func (c *IndexConfig) ListDeprecatedComponents() []ComponentsItem

ListDeprecatedComponents returns all components with Deprecate=true (marked as deprecated)

func (*IndexConfig) ListVisibleComponents

func (c *IndexConfig) ListVisibleComponents() []ComponentsItem

ListVisibleComponents returns all components with Hide=false (publicly visible)

func (*IndexConfig) SaveIndex

func (c *IndexConfig) SaveIndex(filePath string) error

SaveIndex serializes IndexConfig to formatted JSON and writes to file Only writes data (preserves existing Timestamp if no content change)

func (*IndexConfig) SetComponentDeprecate

func (c *IndexConfig) SetComponentDeprecate(name string, deprecate bool) error

SetComponentDeprecate updates the deprecate status of a specific component name: Target component name deprecate: New deprecate status (true = mark as deprecated, false = mark as active) Returns error if component not found, updates timestamp on success

func (*IndexConfig) SetComponentHide

func (c *IndexConfig) SetComponentHide(name string, hide bool) error

SetComponentHide updates the hide status of a specific component name: Target component name hide: New hide status (true = hide from public list, false = show publicly) Returns error if component not found, updates timestamp on success

func (*IndexConfig) UpdateComponent

func (c *IndexConfig) UpdateComponent(updatedItem ComponentsItem) error

UpdateComponent replaces existing component data with updated item (matched by name) Returns error if target component is not found in the index Updates Timestamp automatically on success

type KeepRule

type KeepRule struct {
	Pattern    string // Original rule pattern
	IsNegate   bool   // Whether it's a negation rule (!pattern)
	IsDirOnly  bool   // Whether it only matches directories (ends with /)
	IsRootOnly bool   // Whether it only matches root directory (starts with /)
}

KeepRule defines a single preservation rule (compatible with .gitignore syntax)

type MirrorConfig

type MirrorConfig struct {
	Remote   string `toml:"remote"`    // Remote mirror repository URL
	LocalDir string `toml:"local_dir"` // Local directory to store mirror data (complies with TOML naming conventions)
}

MirrorConfig represents the configuration for mirror management in TOML format

func (*MirrorConfig) Load

func (m *MirrorConfig) Load(path string) error

Load reads TOML file into MirrorConfig (only returns decode error)

func (*MirrorConfig) LoadOrCreate

func (m *MirrorConfig) LoadOrCreate(path string) error

Load reads TOML file into MirrorConfig (only returns decode error)

func (*MirrorConfig) Save

func (m *MirrorConfig) Save(path string) error

Save writes the MirrorConfig to the specified file path Creates the file if it doesn't exist; overwrites if it does File permission is set to 0644 (-rw-r--r--) for security and readability

type MirrorContext

type MirrorContext struct {
	RootConfig MirrorConfig
	GitInfo    gitcmd.SystemGitInfo
	Layout     ComponentsLayout
	Error      error
	// lazy loading
	Index *IndexConfig
	Repo  *git.Repository
	Tree  *git.Worktree
	Hash  string
}
var MirrorCtx MirrorContext

type MirrorStatus

type MirrorStatus struct {
	UncommitFiles  []string
	UntrackedFiles []string
	Headhash       string
}

func GetMirrorStatus

func GetMirrorStatus() (*MirrorStatus, error)

type Serm

type Serm struct {
	Major int // Major version (breaking changes)
	Minor int // Minor version (backward-compatible features)
	Patch int // Patch version (bug fixes)
}

Serm represents a semantic version (x.y.z) Compatible with version format "major.minor.patch"

func FromSerm

func FromSerm(major, minor, patch int) *Serm

FromSerm creates a Serm instance from individual major/minor/patch values

func NewSerm

func NewSerm(version string) *Serm

NewSerm creates a new Serm instance from version string (e.g., "1.2.4") Gracefully handles invalid formats: missing parts default to 0, non-numeric parts default to 0

func (*Serm) AdvanceMajor

func (s *Serm) AdvanceMajor()

AdvanceMajor increments major version, resets minor and patch to 0 e.g., 1.2.4 → 2.0.0

func (*Serm) AdvanceMinor

func (s *Serm) AdvanceMinor()

AdvanceMinor increments minor version, resets patch to 0 e.g., 1.2.4 → 1.3.0

func (*Serm) AdvancePatch

func (s *Serm) AdvancePatch()

AdvancePatch increments patch version (no reset) e.g., 1.2.4 → 1.2.5

func (*Serm) Compare

func (s *Serm) Compare(other *Serm) int

Compare compares current Serm with another Serm version Returns:

1  if current version is NEWER than other
0  if versions are EQUAL
-1 if current version is OLDER than other

Panics if other is nil (enforce non-nil to avoid silent errors)

func (*Serm) Equal

func (s *Serm) Equal(other *Serm) bool

Equal checks if two Serm versions are identical

func (*Serm) MarshalJSON

func (s *Serm) MarshalJSON() ([]byte, error)

MarshalJSON converts Serm to JSON string (compatible with BaselineConfig serialization)

func (*Serm) String

func (s *Serm) String() string

String converts Serm to standard version string (x.y.z)

func (*Serm) UnmarshalJSON

func (s *Serm) UnmarshalJSON(data []byte) error

UnmarshalJSON parses JSON string to Serm (compatible with BaselineConfig deserialization)

type VersionType

type VersionType int

VersionType defines the type of version increment (matches Serm's advance methods)

const (
	Major VersionType = iota + 1 // 1: Major version (breaking changes)
	Minor                        // 2: Minor version (backward-compatible features)
	Patch                        // 3: Patch version (bug fixes)
)

Jump to

Keyboard shortcuts

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