Token导航 LogoToken导航

Agent Skill · 前端设计

survey-analysis(调查分析)

survey-analysis 用于处理 GitHub 仓库、Issue、Pull Request 和代码协作信息,适合在 Codex、Claude、Cursor、Gemini CLI 中需要围绕仓库状态、代码变更或协作事项进行整理时使用。可结合来源仓库、安装命令和原始 README 继续核验具体用法。安装前建议确认权限范围、维护状态,以及是否会触发联网、命令执行或文件读写。

survey-analysis 是前端设计类 Agent Skill,可用宿主为 Codex、Claude、Cursor、Gemini CLI,通过GitHub 仓库获取,权限为需要联网;许可证信息还不明确,第三方扫描已通过,按安装量在前端设计类的 10,216 个 Skill 里排第 8,294。

总安装 297周安装 12GitHub Stars 2下载 93核验 2026-05-01

安装说明

本站只整理中文说明,不托管安装包,也不代用户安装。
GitHub
许可证
unknown

安装方式

通过对话安装

复制提示词发给支持本地命令或 Skills 的 AI 助手,先确认命令和权限,再让它执行。

请帮我安装这个 Agent Skill:survey-analysis(调查分析)
来源仓库:https://github.com/hoanghaoha/survy
仓库路径:skills/survey-analysis
安装命令:
npx skills add https://github.com/hoanghaoha/survy --skill survey-analysis
安装前请先检查当前环境是否支持对应 CLI,并向我确认将要执行的命令、安装目录、联网范围和文件读写权限;确认后再执行。

命令行安装

复制命令到本机终端执行。该命令会通过 npx skills 从第三方来源获取 Skill;本站只展示命令,不托管安装包,也不自动执行。

skills.shnpx skills
npx skills add https://github.com/hoanghaoha/survy --skill survey-analysis

这个 Skill 是做什么的

前端设计类 Skill 关注页面结构、视觉规范和组件写法,输出通常是可运行的界面代码。

survey-analysis 用于处理 GitHub 仓库、Issue、Pull Request 和代码协作信息。适合在 Codex、Claude、Cursor、Gemini CLI 中围绕仓库状态、代码变更或协作事项进行整理。

通过 npx skills add 命令从指定 GitHub 仓库安装,需确认权限与维护状态。使用前应核实是否会触发联网、命令执行或文件读写操作。建议结合原始 README 核验具体用法和功能边界。

来源仓库内路径:skills/survey-analysis

上手步骤

4 步
  1. 1

    确认自己的宿主工具

    公开资料标注支持 Codex、Claude、Cursor、Gemini CLI;先确认自己用的是其中之一,再按对应工具的 Skills 目录放置。

  2. 2

    拿到安装命令

    可以直接复制的命令是 npx skills add https://github.com/hoanghaoha/survy --skill survey-analysis;命令里的占位符换成自己的路径或密钥再执行。

  3. 3

    安装后重启宿主

    命令执行完要完全退出宿主工具再打开,让新装的 Skill 被重新扫描到,否则列表里可能看不到。

  4. 4

    按最小权限试用

    它需要需要联网,先在测试目录或测试账号里跑,确认没问题再放到正式项目。

常见问题

6 条

survey-analysis 怎么安装?

在终端执行 npx skills add https://github.com/hoanghaoha/survy --skill survey-analysis。装完完全退出宿主工具再打开,让它重新扫描本地 Skill。

survey-analysis 支持哪些 AI 工具?

公开资料标注支持 Codex、Claude、Cursor、Gemini CLI。其他工具只要能读取本地 Skill 目录,一般也能手动放进去,但要自己确认触发方式是否一致。

survey-analysis 需要什么权限?

权限级别是需要联网。该 Skill 可能需要联网访问来源站点、仓库或外部 API;具体网络访问范围需要结合源码和 README 复核。

survey-analysis 是免费的吗?

公开资料没有标注明确许可证,收费和商用限制都无法确认。正式使用前请到来源仓库核对授权说明。

survey-analysis 用的人多吗?

公开数据是累计安装 297 次,近一周安装 12 次,下载 93 次,GitHub 2 星。这些数字来自第三方目录统计,只能当作热度参考,不代表质量或安全性。

survey-analysis 安全吗?

第三方扫描结果为通过,但这只覆盖已知的静态检查项,不能替代自己读一遍源码和安装命令。

值得选的地方和要先想清楚的地方

值得选的地方

  • 同时适配 4 种工具,换客户端不用重新找替代品。
  • 第三方扫描已通过,常见的高风险行为没有命中。

先想清楚的地方

  • 许可证没有明确标注,能不能商用、能不能再分发都不确定。
  • 第三方目录整理,版本更新和行为细节以来源仓库为准。

适不适合你

更适合

  • 已经在用 Codex,想直接扩展它能力的人。
  • 需要处理前端设计类任务、又不想每次都手写提示词的人。

不太适合

  • 需要明确授权才能用到公司项目里的场景。
  • 需要厂商级技术支持和 SLA 的生产系统。

前端设计类 Skill 对比

6 个同类
Skill总安装GitHub 星权限许可证扫描
frontend-design

前端设计 · Codex、Claude

8,823,360126,072只读MIT通过
vercel-composition-patterns

Vercel 组合模式 · Codex、Claude

3,858,81625,893需要联网MIT通过
vercel-react-native-skills

Vercel React native skills 前端 · Codex、Claude

2,468,66425,878只读MIT通过
adapt

adapt 搜索 · Codex、Claude

2,027,04023,125操作浏览器未明确通过
bolder

bolder 分析 · Codex、Claude

2,004,28823,130只读未明确通过
survey-analysis

调查分析 · 本页

2972需要联网未明确通过

按安装量取同分类前几名;数字来自第三方目录统计,只作热度参考,不代表质量结论。

SKILL.md 原文

survy — Survey Data Analysis Skill

survy is a lightweight Python library for processing, transforming, and analyzing survey data. Its central design principle is treating survey constructs — especially multiselect questions — as first-class concepts rather than awkward DataFrame workarounds.

Install: Always install the latest version — pip install --upgrade survy Powered by: Polars (all DataFrames returned are Polars, not pandas)


1. Core Objects

Survey

Top-level container. Created via read_* functions — never instantiate directly. Access variables with survey["Q1"]. Print for a compact summary.

Variable

Wraps a single Polars Series plus survey metadata. Key attributes:

AttributeTypeDescription
idstrColumn name (read/write via property)
labelstrHuman-readable label (read/write); defaults to id if unset
vtypeVarTypeOne of VarType.SELECT, VarType.MULTISELECT, VarType.NUMBER
value_indicesdict[str, int]Answer code → numeric index mapping; always empty {} for NUMBER
baseintCount of non-null/non-empty responses
lenintTotal row count including nulls
dtypepolars.DataTypeUnderlying Polars dtype
frequenciespolars.DataFrameFrequency table (value, count, proportion)
spsstrSPSS syntax for this variable

2. Reading Data

All readers return a Survey object. The key challenge survy solves at read time is recognizing multiselect questions — questions where one respondent can choose multiple answers. Raw data encodes these in two very different layouts, and survy needs to know which layout it's looking at so it can merge the data into a single logical variable.

Multiselect: Compact Format vs Wide Format

Compact format stores all selected answers in a single cell, joined by a separator (typically ;). One column = one question.

id,  gender,  hobby
1,   Male,    Sport;Book
2,   Female,  Sport;Movie
3,   Male,    Movie

Here hobby is one column. The cell "Sport;Book" means the respondent chose both Sport and Book. survy splits this cell on the separator to recover the individual choices.

Wide format spreads each possible answer across its own column, using a shared prefix plus a numeric suffix (_1, _2,...). Multiple columns = one question.

id,  gender,  hobby_1,  hobby_2,  hobby_3
1,   Male,    Book,     ,         Sport
2,   Female,  ,         Movie,    Sport
3,   Male,    ,         Movie,

Here hobby_1, hobby_2, hobby_3 are three columns that together represent the single hobby question. survy groups them by matching the prefix pattern and merges them into one multiselect variable named hobby.

After reading, both formats produce the exact same Survey variable internally — a MULTISELECT variable whose data is a sorted list of chosen values per respondent:

hobby: [["Book", "Sport"], ["Movie", "Sport"], ["Movie"]]

How survy detects each format

Wide format is detected via name_pattern — a format template (NOT a raw regex) with two named tokens and a set of reserved separators:

  • Tokens: id (base variable name), multi (suffix for wide columns)
  • Reserved separators: _, ., : — these are always treated as delimiters between tokens when parsing column names

With the default pattern "id(_multi)?":

  • hobby_1 → id="hobby", multi="1" → grouped as wide multiselect
  • hobby_2 → same id="hobby" → merged with hobby_1
  • gender → no suffix → normal column

Other patterns:

  • "id.multi" → matches Q1.1, Q1.2,...
  • "id:multi" → matches Q1:a, Q1:b,...

Separator conflict warning: If a column name contains more than one reserved separator (e.g. my.var_1), parse_id will fail because it can't unambiguously split the name into tokens. Before loading, rename such columns so only one separator is used (e.g. rename my.var_1 to myvar_1 or my@var_1).

Compact format is NOT detected by default because a semicolon in a cell could be regular text. You must tell survy which columns are compact in one of two ways:

  1. compact_ids — explicitly list the column IDs that are compact multiselect.
  2. auto_detect=True — survy scans every column for the compact_separator character; any column containing it in at least one cell is treated as compact.

Rule: Do NOT combine auto_detect=True with compact_ids in the same call.

read_spss

Reads an SPSS .sav file. SPSS files are always wide format — compact multiselect does not apply and compact_ids / auto_detect are not parameters. Wide multiselect columns (e.g. hobby_1, hobby_2) are still auto-detected and merged via name_pattern. Value labels stored in the .sav file are applied automatically, so variables come back as text ("Male", "Female") rather than numeric codes. Requires pyreadstat.

# Wide multiselect detected automatically
survey = survy.read_spss("data.sav")

# Custom suffix convention (Q1.1, Q1.2, ...)
survey = survy.read_spss("data.sav", name_pattern="id.multi")

Rule: Do NOT pass compact_ids or auto_detect to read_spss — those parameters don't exist.


Shared Reader Parameters (read_csv, read_excel, read_polars only)

These parameters control multiselect detection and apply to read_csv, read_excel, and read_polars. They do NOT apply to read_json (which reads survy's own format where variable types are already resolved).

ParameterTypeDefaultDescription
compact_ids`list[str] \None`NoneColumn IDs to treat as compact multiselect
compact_separatorstr";"Separator used to split compact cells
auto_detectboolFalseAuto-detect compact columns by scanning for separator
name_patternstr"id(_multi)?"Format template for wide column names. Tokens: id, multi. Separators: _ . :. Not a raw regex.

read_csv / read_excel

import survy

# --- Compact format data ---

# Option A: you know which columns are compact
survey = survy.read_csv("data_compact.csv", compact_ids=["hobby"], compact_separator=";")

# Option B: let survy scan for the separator automatically
survey = survy.read_csv("data_compact.csv", auto_detect=True, compact_separator=";")

# --- Wide format data ---
# Wide detection is automatic via name_pattern (default works for Q1_1, Q1_2, ...)
survey = survy.read_csv("data_wide.csv")

# Custom name_pattern if your columns use a different suffix convention
survey = survy.read_csv("data_wide.csv", name_pattern="id(_multi)?")

# --- Mixed: some columns are wide, some are compact ---
survey = survy.read_csv("data_mixed.csv", name_pattern="id(_multi)?", auto_detect=True)

# Excel — identical API to read_csv
survey = survy.read_excel("data.xlsx", auto_detect=True, compact_separator=";")

read_json

Reads a survy-format JSON file. The file must have this exact structure:

{
  "variables": [
    {
      "id": "gender",
      "data": ["Male", "Female", "Male"],
      "label": "Gender of respondent",
      "value_indices": {"Female": 1, "Male": 2}
    },
    {
      "id": "yob",
      "data": [2000, 1999, 1998],
      "label": "",
      "value_indices": {}
    },
    {
      "id": "hobby",
      "data": [["Book", "Sport"], ["Movie", "Sport"], ["Movie"]],
      "label": "Hobbies",
      "value_indices": {"Book": 1, "Movie": 2, "Sport": 3}
    }
  ]
}

Key rules for the JSON structure:

  • Top-level key must be "variables" (a list of variable objects).
  • Each variable must have "id", "data", "label", and "value_indices".
  • SELECT variables: "data" is a flat list of strings (or nulls).
  • NUMBER variables: "data" is a flat list of numbers; "value_indices" must be {}.
  • MULTISELECT variables: "data" is a list of lists of strings.
  • "value_indices" maps each answer text to a numeric index; only applied when non-empty.
  • Read vs Write difference: to_json() writes an extra "vtype" field per variable (e.g. "select", "multi_select", "number"). read_json() ignores this field — it re-infers the type from the data. So if you're building JSON manually, you can omit "vtype".
survey = survy.read_json("data.json")

read_polars

Construct a Survey from an existing Polars DataFrame. Extra parameter exclude_null (default True) drops columns with no responses or all-empty lists. read_polars also have same concepts of wide/ compact format as read_csv.

import polars, survy

df = polars.DataFrame({
    "gender": ["Male", "Female", "Male"],
    "yob": [2000, 1999, 1998],
    "hobby": ["Sport;Book", "Sport;Movie", "Movie"],
    "animal_1": ["Cat", "", "Cat"],
    "animal_2": ["Dog", "Dog", ""],
})
survey = survy.read_polars(df, auto_detect=True)

3. Modifying the Survey

survey.update() — batch label/value_indices

survey.update([
    {"id": "Q1", "label": "Satisfaction", "value_indices": {"good": 1, "bad": 2}},
    {"id": "Q2", "label": "Channels used"},
])

Silently skips value_indices for NUMBER variables. Warns and skips unknown IDs.

survey.add() — add a variable

survey.add(some_variable)           # Variable object
survey.add(polars.Series("new", [1, 2, 3]))  # auto-wrapped into Variable

If the ID already exists, a numeric suffix is appended (e.g. "Q1#1").

survey.drop() — remove a variable

survey.drop("Q3")   # silently ignored if not found

survey.sort() — reorder variables

survey.sort()                                      # alphabetical by id (default)
survey.sort(key=lambda v: v.base, reverse=True)    # by response count desc

variable.replace() — recode values

survey["gender"].replace({"Male": "M", "Female": "F"})

Works for both SELECT and MULTISELECT. Automatically rebuilds value_indices.

Direct property assignment

v = survey["Q1"]
v.id = "satisfaction"
v.label = "Overall satisfaction"
v.value_indices = {"very_satisfied": 1, "satisfied": 2, "neutral": 3}

Caution on value_indices setter: Raises DataStructureError if any existing value in the data is missing from the new mapping. You must cover ALL values present in the data.


4. Filtering

Returns a new Survey (original is not mutated).

filtered = survey.filter("hobby", ["Sport", "Book"])
filtered = survey.filter("gender", "Male")   # single value also works

For MULTISELECT, a row is kept if any of its selected values appears in the filter list.


5. Getting a DataFrame

df = survey.get_df(
    select_dtype="text",          # "text" | "number"
    multiselect_dtype="compact",  # "compact" | "text" | "number"
)

select_dtype: "text" keeps string codes (default); "number" converts via value_indices.

multiselect_dtype:

  • "compact" → one List[str] column per multiselect (default)
  • "text" → expands to wide columns Q_1, Q_2,... with string or null
  • "number" → expands to wide columns with 1/0 binary flags

Returns Polars DataFrame — use Polars methods, not pandas.

Valid dtype literals: "text", "number", "compact". Never "numeric" or "string".


6. Analysis

Frequency table

survey["Q1"].frequencies
# → Polars DataFrame: columns [variable_id, "count", "proportion"]

Crosstab

result = survy.crosstab(
    column=survey["gender"],     # grouping variable (columns)
    row=survey["hobby"],         # analyzed variable (rows)
    filter=None,                 # optional: segment by another variable
    aggfunc="count",             # "count" | "percent" | "mean" | "median" | "sum"
    alpha=0.05,                  # significance level for stat tests
)
# Returns dict[str, polars.DataFrame]
# Key is "Total" when no filter, or each filter-value when filter is provided

aggfunc options:

  • "count" — cell counts with significance letter labels (z-test)
  • "percent" — column-wise proportions with significance labels
  • Numeric ("mean", "median", "sum") — aggregates row variable; Welch's t-test for significance

filter: Pass a Variable to segment the crosstab into one table per filter value.


7. Exporting

All exports take a directory path (not file path) + optional name (base filename).

to_csv / to_excel

Writes three files per export:

  • {name}_data.csv — the actual survey responses. Format depends on compact param.
  • {name}_variables_info.csv — variable metadata with columns: id, vtype (SINGLE/MULTISELECT/NUMBER), label.
  • {name}_values_info.csv — value-to-index mappings with columns: id, text, index.

The compact parameter (default False) controls how multiselect variables appear in the data file: True joins values into one cell (e.g. "Book;Sport"), False expands into wide columns (e.g. hobby_1, hobby_2, hobby_3).

# Default (compact=False) — multiselect expanded to wide columns
survey.to_csv("output/", name="results")

# Compact mode — multiselect joined into single cells
survey.to_csv("output/", name="results", compact=True, compact_separator=";")

# Excel — identical API and output structure (.xlsx files instead of .csv)
survey.to_excel("output/", name="results")
survey.to_excel("output/", name="results", compact=True)

to_spss

Writes {name}.sav (data) + {name}.sps (syntax). Requires pyreadstat.

survey.to_spss("output/", name="results")

to_json

Writes {name}.json in the same structure read_json expects (see Section 2), plus an extra "vtype" field per variable that read_json ignores on re-read. Pretty-printed with 4-space indent, non-ASCII preserved (ensure_ascii=False).

survey.to_json("output/", name="results")

Common mistake: Do NOT pass "output/results.csv". Pass directory + name=.

SPSS Syntax

print(survey.sps)  # full syntax: VARIABLE LABELS, VALUE LABELS, MRSETS, CTABLES

8. Gotchas & Rules

  1. auto_detect vs compact_ids: Never combine both.
  2. value_indices setter must cover all existing data values — raises DataStructureError otherwise.
  3. value_indices is silently skipped for NUMBER variables (in update() and direct set).
  4. Export path is a directory, not a file.
  5. get_df() returns Polars, not pandas.
  6. filter() returns a new Survey — does not mutate.
  7. Empty strings become None during CSV/Excel read.
  8. Multiselect values are sorted alphabetically within each row.
  9. All variables in a crosstab must have the same row count.
  10. read_csv raises FileTypeError if the file extension is not .csv. Same for read_excel with non-.xlsx and read_spss with non-.sav.
  11. to_csv/to_excel default is compact=False — multiselect variables are expanded to wide columns unless you explicitly pass compact=True.
  12. Column names must not contain multiple reserved separators (_, ., :). If a column like my.var_1 uses more than one, parse_id will fail. Rename before loading so only one separator appears (e.g. myvar_1).

9. Quick Reference

TaskCode
Load CSV auto-detectsurvy.read_csv("f.csv", auto_detect=True, compact_separator=";")
Load CSV explicit compactsurvy.read_csv("f.csv", compact_ids=["Q2"], compact_separator=";")
Load CSV wide formatsurvy.read_csv("f.csv", name_pattern="id(_multi)?") (wide detected automatically)
Load SPSSsurvy.read_spss("f.sav")
Load JSONsurvy.read_json("f.json")
Load from Polars DFsurvy.read_polars(df, auto_detect=True)
Inspect variablesurvey["Q1"].vtype, .base, .len, .label, .value_indices, .dtype
Frequenciessurvey["Q1"].frequencies
Crosstab countsurvy.crosstab(survey["Q1"], survey["Q2"])
Crosstab percentsurvy.crosstab(survey["Q1"], survey["Q2"], aggfunc="percent")
Crosstab with filtersurvy.crosstab(survey["col"], survey["row"], filter=survey["seg"])
Crosstab meansurvy.crosstab(survey["col"], survey["row"], aggfunc="mean")
Filter respondentssurvey.filter("Q1", ["a", "b"])
Replace valuessurvey["Q1"].replace({"old": "new"})
Add variablesurvey.add(polars.Series("x", [1,2,3]))
Drop variablesurvey.drop("Q3")
Sort variablessurvey.sort(key=lambda v: v.id)
Batch update labelssurvey.update([{"id":"Q1","label":"...","value_indices":{...}}])
Get compact DFsurvey.get_df()
Get wide binary DFsurvey.get_df(multiselect_dtype="number")
Export CSVsurvey.to_csv("output/", name="results")
Export SPSSsurvey.to_spss("output/", name="results")
Export JSONsurvey.to_json("output/", name="results")
SPSS syntax stringsurvey.sps
Serialize variablesurvey["Q1"].to_dict()

10. Reference Files

  • references/api_reference.md — Complete method signatures with all parameters and return types
  • scripts/validate_survey.py — Loads a survey file, checks missing labels/value_indices, prints report
  • scripts/batch_export.py — Reads a survey and exports to CSV, Excel, SPSS, and JSON
  • assets/sample_data.csv — Wide-format sample dataset
  • assets/sample_data_compact.csv — Compact-format sample dataset

平台分布

Codex

37.31%
按下载量换算35

Claude

26.31%
按下载量换算24

Cursor

17.51%
按下载量换算16

Gemini CLI

9.68%
按下载量换算9

安全审计

Gen Agent Trust Hub

通过

Socket

通过

Snyk

通过

权限和风险

需要联网

该 Skill 可能需要联网访问来源站点、仓库或外部 API;具体网络访问范围需要结合源码和 README 复核。

安装前确认

本站仅展示第三方公开信息,不托管安装包,不提供自动安装或运行环境。安装前应自行审查源码、依赖和命令行为。目前只有一个公开来源,建议同时核对源仓库。

继续浏览同类 Skills