• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

ZJU-SPAIL / pipa / 22699554347

05 Mar 2026 02:33AM UTC coverage: 19.922% (-50.1%) from 70.041%
22699554347

push

github

Rui Hu
Merge github/main, resolve two version conflicts by keeping gitlab local

6 of 2484 new or added lines in 35 files covered. (0.24%)

871 of 4372 relevant lines covered (19.92%)

0.2 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

0.0
/src/pipa/analysis/flamegraph/csv_export.py
1
# -*- coding: utf-8 -*-
NEW
2
from __future__ import annotations
×
3

NEW
4
import csv
×
NEW
5
from typing import Iterable, Optional, Union
×
6

NEW
7
from pipa.analysis.flamegraph.analyzer import (
×
8
    SymbolStat,
9
    StackStat,
10
    SymbolShare,
11
    StackShare,
12
)
13

14
# The CSV writers accept either raw stats or enriched shares.
15
# If enriched shares are provided, percentage columns are written directly.
16
# Otherwise, if a total is provided, percentages are computed on the fly for backward compatibility.
17

18

NEW
19
def write_symbol_stats_csv(
×
20
    path: str,
21
    stats: Iterable[Union[SymbolStat, SymbolShare]],
22
    total: Optional[int] = None,
23
) -> None:
NEW
24
    with open(path, "w", newline="", encoding="utf-8") as f:
×
NEW
25
        writer = csv.writer(f)
×
NEW
26
        first = None
×
NEW
27
        for first in stats:
×
NEW
28
            break
×
29
        # Recreate iterator: if we consumed one, we need to write it back.
NEW
30
        if first is None:
×
NEW
31
            (
×
32
                writer.writerow(["symbol", "inclusive", "leaf"])
33
                if not total
34
                else writer.writerow(
35
                    [
36
                        "symbol",
37
                        "inclusive",
38
                        "inclusive_pct",
39
                        "leaf",
40
                        "leaf_pct",
41
                    ]
42
                )
43
            )
NEW
44
            return
×
45
        # Determine mode by instance type
NEW
46
        is_share = isinstance(first, SymbolShare)
×
47
        # Write header
NEW
48
        if is_share:
×
NEW
49
            writer.writerow(
×
50
                ["symbol", "inclusive", "inclusive_pct", "leaf", "leaf_pct"]
51
            )
NEW
52
        elif total and total > 0:
×
NEW
53
            writer.writerow(
×
54
                ["symbol", "inclusive", "inclusive_pct", "leaf", "leaf_pct"]
55
            )
56
        else:
NEW
57
            writer.writerow(["symbol", "inclusive", "leaf"])
×
58
        # Write first row then the rest
59

NEW
60
        def write_row(s):
×
NEW
61
            if is_share:
×
NEW
62
                writer.writerow(
×
63
                    [
64
                        s.symbol,
65
                        s.inclusive,
66
                        f"{s.inclusive_pct:.2f}%",
67
                        s.leaf,
68
                        f"{s.leaf_pct:.2f}%",
69
                    ]
70
                )
NEW
71
            elif total and total > 0:
×
NEW
72
                inc_pct = (s.inclusive / total) * 100.0
×
NEW
73
                leaf_pct = (s.leaf / total) * 100.0
×
NEW
74
                writer.writerow(
×
75
                    [
76
                        s.symbol,
77
                        s.inclusive,
78
                        f"{inc_pct:.2f}%",
79
                        s.leaf,
80
                        f"{leaf_pct:.2f}%",
81
                    ]
82
                )
83
            else:
NEW
84
                writer.writerow([s.symbol, s.inclusive, s.leaf])
×
85

NEW
86
        write_row(first)
×
NEW
87
        for s in stats:
×
NEW
88
            write_row(s)
×
89

90

NEW
91
def write_stack_stats_csv(
×
92
    path: str,
93
    stacks: Iterable[Union[StackStat, StackShare]],
94
    total: Optional[int] = None,
95
) -> None:
NEW
96
    with open(path, "w", newline="", encoding="utf-8") as f:
×
NEW
97
        writer = csv.writer(f)
×
NEW
98
        first = None
×
NEW
99
        for first in stacks:
×
NEW
100
            break
×
NEW
101
        if first is None:
×
NEW
102
            (
×
103
                writer.writerow(["stack", "weight"])
104
                if not total
105
                else writer.writerow(
106
                    [
107
                        "stack",
108
                        "weight",
109
                        "weight_pct",
110
                    ]
111
                )
112
            )
NEW
113
            return
×
NEW
114
        is_share = isinstance(first, StackShare)
×
NEW
115
        if is_share:
×
NEW
116
            writer.writerow(["stack", "weight", "weight_pct"])
×
NEW
117
        elif total and total > 0:
×
NEW
118
            writer.writerow(["stack", "weight", "weight_pct"])
×
119
        else:
NEW
120
            writer.writerow(["stack", "weight"])
×
121

NEW
122
        def write_row(s):
×
NEW
123
            if is_share:
×
NEW
124
                writer.writerow([s.stack, s.weight, f"{s.weight_pct:.2f}%"])
×
NEW
125
            elif total and total > 0:
×
NEW
126
                weight_pct = (s.weight / total) * 100.0
×
NEW
127
                writer.writerow([s.stack, s.weight, f"{weight_pct:.2f}%"])
×
128
            else:
NEW
129
                writer.writerow([s.stack, s.weight])
×
130

NEW
131
        write_row(first)
×
NEW
132
        for s in stacks:
×
NEW
133
            write_row(s)
×
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc