Function bodies 401 total
Component function · go · L27-L37 (11 LOC)component.go
func Component(cfg ComponentConfig) *engine.Component {
return &engine.Component{
Namespace: "rca",
Name: "origami-rca",
Version: "1.0.0",
Description: "RCA circuit plumbing for CI root-cause analysis",
Transformers: buildTransformers(cfg),
Extractors: buildExtractors(cfg.CircuitDef),
Hooks: buildHooks(cfg),
}
}nodeNames function · go · L45-L52 (8 LOC)component.go
func nodeNames(cd *circuit.CircuitDef) []string {
if cd != nil {
if names := engine.NodeNamesFromCircuit(cd); len(names) > 0 {
return names
}
}
return allNodeNames
}HeuristicComponent function · go · L56-L71 (16 LOC)component.go
func HeuristicComponent(st store.Store, repos []string, heuristicsData []byte) *engine.Component {
ht := NewHeuristicTransformer(st, repos, heuristicsData)
return &engine.Component{
Namespace: "rca",
Name: "rca-heuristic",
Transformers: engine.TransformerRegistry{
"recall": &recallHeuristic{ht: ht},
"triage": &triageHeuristic{ht: ht},
"resolve": &resolveHeuristic{ht: ht},
"investigate": &investigateHeuristic{ht: ht},
"correlate": &correlateHeuristic{ht: ht},
"review": &reviewHeuristic{},
"report": &reportHeuristic{},
},
}
}TransformerComponent function · go · L78-L88 (11 LOC)component.go
func TransformerComponent(t engine.Transformer, cd ...*circuit.CircuitDef) *engine.Component {
var def *circuit.CircuitDef
if len(cd) > 0 {
def = cd[0]
}
return &engine.Component{
Namespace: "rca",
Name: "rca-transformer",
Transformers: engine.TransformerForAllNodes(t, nodeNames(def)),
}
}HITLComponent function · go · L94-L108 (15 LOC)component.go
func HITLComponent(cd ...*circuit.CircuitDef) *engine.Component {
var def *circuit.CircuitDef
if len(cd) > 0 {
def = cd[0]
}
reg := engine.TransformerRegistry{}
for _, name := range nodeNames(def) {
reg[name] = &hitlTransformerNode{nodeName: name}
}
return &engine.Component{
Namespace: "rca",
Name: "rca-hitl",
Transformers: reg,
}
}buildTransformers function · go · L110-L112 (3 LOC)component.go
func buildTransformers(_ ComponentConfig) engine.TransformerRegistry {
return engine.TransformerRegistry{}
}buildExtractors function · go · L114-L118 (5 LOC)component.go
func buildExtractors(cd *circuit.CircuitDef) engine.ExtractorRegistry {
return engine.ExtractorForAllNodes(func(name string) engine.Extractor {
return NewMapExtractor(name)
}, nodeNames(cd))
}Repobility · MCP-ready · https://repobility.com
buildHooks function · go · L120-L141 (22 LOC)component.go
func buildHooks(cfg ComponentConfig) engine.HookRegistry {
reg := engine.HookRegistry{}
inject := InjectHooksWithOpts(InjectHookOpts{
Store: cfg.Store,
CaseData: cfg.CaseData,
Envelope: cfg.Envelope,
Catalog: cfg.Catalog,
CaseDir: cfg.CaseDir,
})
for name, h := range inject {
reg[name] = h
}
if cfg.Store != nil && cfg.CaseData != nil {
hooks := StoreHooks(cfg.Store, cfg.CaseData)
for name, h := range hooks {
reg[name] = h
}
}
return reg
}WithHTTPClient function · go · L74-L79 (6 LOC)connectors/rp/client.go
func WithHTTPClient(c *http.Client) Option {
return func(cfg *clientConfig) error {
cfg.httpClient = c
return nil
}
}WithLogger function · go · L82-L87 (6 LOC)connectors/rp/client.go
func WithLogger(l *slog.Logger) Option {
return func(cfg *clientConfig) error {
cfg.logger = l
return nil
}
}WithTimeout function · go · L90-L95 (6 LOC)connectors/rp/client.go
func WithTimeout(d time.Duration) Option {
return func(cfg *clientConfig) error {
cfg.timeout = d
return nil
}
}doJSON method · go · L99-L140 (42 LOC)connectors/rp/client.go
func (c *Client) doJSON(ctx context.Context, method, url, operation string, body io.Reader, dst any) error {
req, err := http.NewRequestWithContext(ctx, method, url, body)
if err != nil {
return fmt.Errorf("%s: create request: %w", operation, err)
}
if c.token != "" {
req.Header.Set("Authorization", "Bearer "+c.token)
}
if body != nil {
req.Header.Set("Content-Type", "application/json")
}
c.logger.InfoContext(ctx, "API request", "operation", operation, "method", method, "url", url)
resp, err := c.httpClient.Do(req)
if err != nil {
return fmt.Errorf("%s: do request: %w", operation, err)
}
defer resp.Body.Close()
c.logger.DebugContext(ctx, "API response", "operation", operation, "status", resp.StatusCode)
if resp.StatusCode < 200 || resp.StatusCode >= 300 {
respBody, _ := io.ReadAll(resp.Body)
var errRS ErrorRS
if json.Unmarshal(respBody, &errRS) == nil && errRS.Message != "" {
return newAPIError(operation, resp.StatusCode, errRS.ErrorCode, errRS.MessagGetCurrentUser method · go · L144-L151 (8 LOC)connectors/rp/client.go
func (c *Client) GetCurrentUser(ctx context.Context) (*UserResource, error) {
u := fmt.Sprintf("%s/users", c.baseURL)
var user UserResource
if err := c.doJSON(ctx, "GET", u, "get current user", nil, &user); err != nil {
return nil, err
}
return &user, nil
}ReadAPIKey function · go · L154-L161 (8 LOC)connectors/rp/client.go
func ReadAPIKey(path string) (string, error) {
data, err := os.ReadFile(path)
if err != nil {
return "", err
}
line := strings.TrimSpace(strings.Split(string(data), "\n")[0])
return line, nil
}FetchEnvelope method · go · L11-L74 (64 LOC)connectors/rp/envelope.go
func (p *ProjectScope) FetchEnvelope(ctx context.Context, launchID int) (*Envelope, error) {
launch, err := p.Launches().Get(ctx, launchID)
if err != nil {
return nil, fmt.Errorf("fetch envelope: get launch: %w", err)
}
items, err := p.Items().ListAll(ctx,
WithLaunchID(launchID),
WithStatus("FAILED"),
)
if err != nil {
return nil, fmt.Errorf("fetch envelope: list items: %w", err)
}
env := &Envelope{
RunID: strconv.Itoa(launch.ID),
LaunchUUID: launch.UUID,
Name: launch.Name,
FailureList: make([]FailureItem, 0, len(items)),
}
for _, attr := range launch.Attributes {
env.LaunchAttributes = append(env.LaunchAttributes, Attribute{
Key: attr.Key,
Value: attr.Value,
System: attr.System,
})
}
for _, it := range items {
path := it.Path
if path == "" {
path = strconv.Itoa(it.ID)
}
fi := FailureItem{
ID: it.ID,
UUID: it.UUID,
Name: it.Name,
Type: it.Type,
Status: it.Status,
Path: path,
CodeWant fix-PRs on findings? Install Repobility's GitHub App · github.com/apps/repobility-bot
Error method · go · L19-L24 (6 LOC)connectors/rp/errors.go
func (e *APIError) Error() string {
if e.errorCode != 0 {
return fmt.Sprintf("%s: HTTP %d: [%d] %s", e.operation, e.statusCode, e.errorCode, e.message)
}
return fmt.Sprintf("%s: HTTP %d: %s", e.operation, e.statusCode, e.message)
}newAPIError function · go · L26-L33 (8 LOC)connectors/rp/errors.go
func newAPIError(operation string, statusCode int, errorCode int, message string) *APIError {
return &APIError{
operation: operation,
statusCode: statusCode,
errorCode: errorCode,
message: message,
}
}HasStatusCode function · go · L57-L60 (4 LOC)connectors/rp/errors.go
func HasStatusCode(err error, code int) bool {
var apiErr *APIError
return errors.As(err, &apiErr) && apiErr.statusCode == code
}HasErrorCode function · go · L63-L66 (4 LOC)connectors/rp/errors.go
func HasErrorCode(err error, code int) bool {
var apiErr *APIError
return errors.As(err, &apiErr) && apiErr.errorCode == code
}NewFetcher function · go · L13-L15 (3 LOC)connectors/rp/fetcher.go
func NewFetcher(client *Client, project string) *Fetcher {
return &Fetcher{client: client, project: project}
}Fetch method · go · L18-L20 (3 LOC)connectors/rp/fetcher.go
func (f *Fetcher) Fetch(launchID int) (*Envelope, error) {
return f.client.Project(f.project).FetchEnvelope(context.Background(), launchID)
}Analyze method · go · L20-L22 (3 LOC)connectors/rp/invest_analyze.go
func (DefaultAnalyzer) Analyze(src EnvelopeSource, launchID int, artifactPath string) error {
return Analyze(src, launchID, artifactPath)
}Analyze function · go · L26-L28 (3 LOC)connectors/rp/invest_analyze.go
func Analyze(src EnvelopeSource, launchID int, artifactPath string) error {
return AnalyzeWithCatalog(src, launchID, artifactPath, nil)
}Generated by Repobility's multi-pass static-analysis pipeline (https://repobility.com)
AnalyzeWithCatalog function · go · L32-L54 (23 LOC)connectors/rp/invest_analyze.go
func AnalyzeWithCatalog(src EnvelopeSource, launchID int, artifactPath string, cat toolkit.SourceCatalog) error {
env, err := src.Get(launchID)
if err != nil {
return err
}
if env == nil {
return nil
}
_ = cat // used by prompts when building context; artifact unchanged for PoC
artifact := Artifact{
LaunchID: env.RunID,
CaseIDs: CaseIDsFromEnvelope(env),
RCAMessage: "",
DefectType: "ti001",
ConvergenceScore: 0.85,
EvidenceRefs: []string{},
}
data, err := json.MarshalIndent(artifact, "", " ")
if err != nil {
return err
}
return os.WriteFile(artifactPath, data, 0644)
}CaseIDsFromEnvelope function · go · L5-L14 (10 LOC)connectors/rp/invest_cases.go
func CaseIDsFromEnvelope(env *Envelope) []int {
if env == nil {
return nil
}
ids := make([]int, 0, len(env.FailureList))
for _, f := range env.FailureList {
ids = append(ids, f.ID)
}
return ids
}List method · go · L22-L36 (15 LOC)connectors/rp/item.go
func (s *ItemScope) List(ctx context.Context, opts ...ListItemsOption) (*PagedItems, error) {
params := url.Values{}
for _, opt := range opts {
opt(params)
}
u := fmt.Sprintf("%s/api/v1/%s/item?%s",
s.project.client.baseURL, s.project.projectName, params.Encode())
var paged PagedItems
if err := s.project.client.doJSON(ctx, "GET", u, "list items", nil, &paged); err != nil {
return nil, err
}
return &paged, nil
}ListAll method · go · L39-L60 (22 LOC)connectors/rp/item.go
func (s *ItemScope) ListAll(ctx context.Context, opts ...ListItemsOption) ([]TestItemResource, error) {
var all []TestItemResource
page := 1
pageSize := 200
for {
pageOpts := append(opts,
WithItemPageSize(pageSize),
WithItemPageNumber(page),
)
paged, err := s.List(ctx, pageOpts...)
if err != nil {
return nil, err
}
all = append(all, paged.Content...)
if len(paged.Content) < pageSize {
break
}
page++
}
return all, nil
}Get method · go · L63-L72 (10 LOC)connectors/rp/item.go
func (s *ItemScope) Get(ctx context.Context, id int) (*TestItemResource, error) {
u := fmt.Sprintf("%s/api/v1/%s/item/%d",
s.project.client.baseURL, s.project.projectName, id)
var item TestItemResource
if err := s.project.client.doJSON(ctx, "GET", u, "get item", nil, &item); err != nil {
return nil, err
}
return &item, nil
}UpdateDefect method · go · L75-L90 (16 LOC)connectors/rp/item.go
func (s *ItemScope) UpdateDefect(ctx context.Context, itemID int, defectType string) error {
u := fmt.Sprintf("%s/api/v1/%s/item/%d/update",
s.project.client.baseURL, s.project.projectName, itemID)
body := map[string]any{
"issues": []map[string]any{
{"issueType": defectType},
},
}
payload, err := json.Marshal(body)
if err != nil {
return fmt.Errorf("update defect: marshal: %w", err)
}
return s.project.client.doJSON(ctx, "PUT", u, "update defect", bytes.NewReader(payload), nil)
}UpdateDefectBulk method · go · L93-L106 (14 LOC)connectors/rp/item.go
func (s *ItemScope) UpdateDefectBulk(ctx context.Context, definitions []IssueDefinition) error {
u := fmt.Sprintf("%s/api/v1/%s/item",
s.project.client.baseURL, s.project.projectName)
body := map[string]any{
"issues": definitions,
}
payload, err := json.Marshal(body)
if err != nil {
return fmt.Errorf("update defect bulk: marshal: %w", err)
}
return s.project.client.doJSON(ctx, "PUT", u, "update defect bulk", bytes.NewReader(payload), nil)
}WithLaunchID function · go · L111-L113 (3 LOC)connectors/rp/item.go
func WithLaunchID(id int) ListItemsOption {
return func(p url.Values) { p.Set("filter.eq.launchId", strconv.Itoa(id)) }
}Repobility · severity-and-effort ranking · https://repobility.com
WithStatus function · go · L116-L118 (3 LOC)connectors/rp/item.go
func WithStatus(status string) ListItemsOption {
return func(p url.Values) { p.Set("filter.eq.status", status) }
}WithItemType function · go · L121-L123 (3 LOC)connectors/rp/item.go
func WithItemType(itemType string) ListItemsOption {
return func(p url.Values) { p.Set("filter.eq.type", itemType) }
}WithItemPageSize function · go · L126-L128 (3 LOC)connectors/rp/item.go
func WithItemPageSize(size int) ListItemsOption {
return func(p url.Values) { p.Set("page.size", strconv.Itoa(size)) }
}WithItemPageNumber function · go · L131-L133 (3 LOC)connectors/rp/item.go
func WithItemPageNumber(n int) ListItemsOption {
return func(p url.Values) { p.Set("page.page", strconv.Itoa(n)) }
}NewRunDiscoverer function · go · L19-L29 (11 LOC)connectors/rp/launch_fetcher.go
func NewRunDiscoverer(baseURL, apiKeyPath, project string) (rcatype.RunDiscoverer, error) {
key, err := ReadAPIKey(apiKeyPath)
if err != nil {
return nil, err
}
client, err := New(baseURL, key, WithTimeout(30*time.Second))
if err != nil {
return nil, err
}
return &RPRunDiscoverer{client: client, project: project}, nil
}DiscoverRuns method · go · L31-L67 (37 LOC)connectors/rp/launch_fetcher.go
func (f *RPRunDiscoverer) DiscoverRuns(project string, since time.Time) ([]rcatype.RunInfo, error) {
ctx := context.Background()
paged, err := f.client.Project(project).Launches().List(ctx,
WithPageSize(100),
WithSort("startTime,desc"),
)
if err != nil {
return nil, err
}
var runs []rcatype.RunInfo
for _, l := range paged.Content {
var startTime time.Time
if l.StartTime != nil {
startTime = l.StartTime.Time()
}
if !since.IsZero() && startTime.Before(since) {
continue
}
failed := 0
if l.Statistics != nil {
if execs, ok := l.Statistics.Executions["failed"]; ok {
failed = execs
}
}
runs = append(runs, rcatype.RunInfo{
ID: l.ID,
UUID: l.UUID,
Name: l.Name,
Number: l.Number,
Status: l.Status,
StartTime: startTime,
FailedCount: failed,
})
}
return runs, nil
}FetchFailures method · go · L69-L95 (27 LOC)connectors/rp/launch_fetcher.go
func (f *RPRunDiscoverer) FetchFailures(runID int) ([]rcatype.FailureInfo, error) {
ctx := context.Background()
items, err := f.client.Project(f.project).Items().ListAll(ctx,
WithLaunchID(runID),
WithStatus("FAILED"),
)
if err != nil {
return nil, err
}
var failures []rcatype.FailureInfo
for _, item := range items {
fi := rcatype.FailureInfo{
RunID: runID,
ItemID: item.ID,
ItemUUID: item.UUID,
TestName: item.Name,
Status: item.Status,
}
if item.Issue != nil {
fi.IssueType = item.Issue.IssueType
fi.AutoAnalyzed = item.Issue.AutoAnalyzed
}
failures = append(failures, fi)
}
return failures, nil
}Get method · go · L16-L25 (10 LOC)connectors/rp/launch.go
func (l *LaunchScope) Get(ctx context.Context, id int) (*LaunchResource, error) {
u := fmt.Sprintf("%s/api/v1/%s/launch/%d",
l.project.client.baseURL, l.project.projectName, id)
var launch LaunchResource
if err := l.project.client.doJSON(ctx, "GET", u, "get launch", nil, &launch); err != nil {
return nil, err
}
return &launch, nil
}Repobility · MCP-ready · https://repobility.com
GetByUUID method · go · L28-L37 (10 LOC)connectors/rp/launch.go
func (l *LaunchScope) GetByUUID(ctx context.Context, uuid string) (*LaunchResource, error) {
u := fmt.Sprintf("%s/api/v1/%s/launch/uuid/%s",
l.project.client.baseURL, l.project.projectName, uuid)
var launch LaunchResource
if err := l.project.client.doJSON(ctx, "GET", u, "get launch by uuid", nil, &launch); err != nil {
return nil, err
}
return &launch, nil
}List method · go · L43-L57 (15 LOC)connectors/rp/launch.go
func (l *LaunchScope) List(ctx context.Context, opts ...ListLaunchesOption) (*PagedLaunches, error) {
params := url.Values{}
for _, opt := range opts {
opt(params)
}
u := fmt.Sprintf("%s/api/v1/%s/launch?%s",
l.project.client.baseURL, l.project.projectName, params.Encode())
var paged PagedLaunches
if err := l.project.client.doJSON(ctx, "GET", u, "list launches", nil, &paged); err != nil {
return nil, err
}
return &paged, nil
}WithLaunchName function · go · L60-L62 (3 LOC)connectors/rp/launch.go
func WithLaunchName(name string) ListLaunchesOption {
return func(p url.Values) { p.Set("filter.eq.name", name) }
}WithLaunchStatus function · go · L65-L67 (3 LOC)connectors/rp/launch.go
func WithLaunchStatus(status string) ListLaunchesOption {
return func(p url.Values) { p.Set("filter.eq.status", status) }
}WithPageSize function · go · L70-L72 (3 LOC)connectors/rp/launch.go
func WithPageSize(size int) ListLaunchesOption {
return func(p url.Values) { p.Set("page.size", strconv.Itoa(size)) }
}WithPageNumber function · go · L75-L77 (3 LOC)connectors/rp/launch.go
func WithPageNumber(n int) ListLaunchesOption {
return func(p url.Values) { p.Set("page.page", strconv.Itoa(n)) }
}WithSort function · go · L80-L82 (3 LOC)connectors/rp/launch.go
func WithSort(sort string) ListLaunchesOption {
return func(p url.Values) { p.Set("page.sort", sort) }
}Push method · go · L28-L30 (3 LOC)connectors/rp/postinvest_push.go
func (DefaultDefectPusher) Push(artifactPath string, store PushStore, jiraTicketID, jiraLink string) error {
return Push(artifactPath, store, jiraTicketID, jiraLink)
}Want fix-PRs on findings? Install Repobility's GitHub App · github.com/apps/repobility-bot
Push function · go · L35-L51 (17 LOC)connectors/rp/postinvest_push.go
func Push(artifactPath string, store PushStore, jiraTicketID, jiraLink string) error {
data, err := os.ReadFile(artifactPath)
if err != nil {
return err
}
var a pushArtifact
if err := json.Unmarshal(data, &a); err != nil {
return err
}
return store.RecordPushed(PushedRecord{
RunID: a.RunID,
CaseIDs: a.CaseIDs,
DefectType: a.DefectType,
JiraTicketID: jiraTicketID,
JiraLink: jiraLink,
})
}NewMemPushStore function · go · L24-L26 (3 LOC)connectors/rp/postinvest_push_store.go
func NewMemPushStore() *MemPushStore {
return &MemPushStore{}
}RecordPushed method · go · L29-L32 (4 LOC)connectors/rp/postinvest_push_store.go
func (s *MemPushStore) RecordPushed(record PushedRecord) error {
s.last = &record
return nil
}