Metadata-Version: 2.4
Name: dp_wizard
Version: 0.4.1
Summary: DP Wizard makes it easier to get started with Differential Privacy.
Keywords: differential privacy
Author-email: The OpenDP Project <info@opendp.org>
Description-Content-Type: text/markdown
Classifier: Programming Language :: Python :: 3
Classifier: License :: OSI Approved :: MIT License
License-File: LICENSE
Requires-Dist: dp-wizard-templates==0.2.0
Requires-Dist: faicons
Requires-Dist: matplotlib
Requires-Dist: opendp[polars]==0.13.0
Requires-Dist: pillow>=11.3.0
Requires-Dist: requests>=2.32.4
Requires-Dist: shiny
Requires-Dist: starlette>=0.47.2
Requires-Dist: tornado>=6.5
Requires-Dist: urllib3>=2.5.0
Requires-Dist: anyio==4.9.0 ; extra == "app"
Requires-Dist: appdirs==1.4.4 ; extra == "app"
Requires-Dist: appnope==0.1.4 ; extra == "app"
Requires-Dist: asgiref==3.8.1 ; extra == "app"
Requires-Dist: asttokens==3.0.0 ; extra == "app"
Requires-Dist: attrs==25.3.0 ; extra == "app"
Requires-Dist: beautifulsoup4==4.13.4 ; extra == "app"
Requires-Dist: black==25.1.0 ; extra == "app"
Requires-Dist: bleach[css]==6.2.0 ; extra == "app"
Requires-Dist: certifi==2025.4.26 ; extra == "app"
Requires-Dist: charset-normalizer==3.4.2 ; extra == "app"
Requires-Dist: click==8.1.8 ; extra == "app"
Requires-Dist: comm==0.2.2 ; extra == "app"
Requires-Dist: contourpy==1.3.2 ; extra == "app"
Requires-Dist: cycler==0.12.1 ; extra == "app"
Requires-Dist: debugpy==1.8.14 ; extra == "app"
Requires-Dist: decorator==5.2.1 ; extra == "app"
Requires-Dist: defusedxml==0.7.1 ; extra == "app"
Requires-Dist: deprecated==1.2.18 ; extra == "app"
Requires-Dist: dp-wizard-templates==0.2.0 ; extra == "app"
Requires-Dist: exceptiongroup==1.3.0 ; extra == "app"
Requires-Dist: executing==2.2.0 ; extra == "app"
Requires-Dist: faicons==0.2.2 ; extra == "app"
Requires-Dist: fastjsonschema==2.21.1 ; extra == "app"
Requires-Dist: fonttools==4.57.0 ; extra == "app"
Requires-Dist: h11==0.16.0 ; extra == "app"
Requires-Dist: htmltools==0.6.0 ; extra == "app"
Requires-Dist: idna==3.10 ; extra == "app"
Requires-Dist: ipykernel==6.29.5 ; extra == "app"
Requires-Dist: ipython==8.35.0 ; extra == "app"
Requires-Dist: jedi==0.19.2 ; extra == "app"
Requires-Dist: jinja2==3.1.6 ; extra == "app"
Requires-Dist: joblib==1.4.2 ; extra == "app"
Requires-Dist: jsonschema-specifications==2024.10.1 ; extra == "app"
Requires-Dist: jsonschema==4.23.0 ; extra == "app"
Requires-Dist: jupyter-client==8.6.3 ; extra == "app"
Requires-Dist: jupyter-core==5.7.2 ; extra == "app"
Requires-Dist: jupyterlab-pygments==0.3.0 ; extra == "app"
Requires-Dist: jupytext==1.17.0 ; extra == "app"
Requires-Dist: kiwisolver==1.4.8 ; extra == "app"
Requires-Dist: linkify-it-py==2.0.3 ; extra == "app"
Requires-Dist: markdown-it-py==3.0.0 ; extra == "app"
Requires-Dist: markupsafe==3.0.2 ; extra == "app"
Requires-Dist: matplotlib-inline==0.1.7 ; extra == "app"
Requires-Dist: matplotlib==3.10.1 ; extra == "app"
Requires-Dist: mdit-py-plugins==0.4.2 ; extra == "app"
Requires-Dist: mdurl==0.1.2 ; extra == "app"
Requires-Dist: mistune==3.1.3 ; extra == "app"
Requires-Dist: mypy-extensions==1.1.0 ; extra == "app"
Requires-Dist: narwhals==1.35.0 ; extra == "app"
Requires-Dist: nbclient==0.10.2 ; extra == "app"
Requires-Dist: nbconvert==7.16.6 ; extra == "app"
Requires-Dist: nbformat==5.10.4 ; extra == "app"
Requires-Dist: nest-asyncio==1.6.0 ; extra == "app"
Requires-Dist: numpy==2.2.4 ; extra == "app"
Requires-Dist: opendp[polars]==0.13.0 ; extra == "app"
Requires-Dist: orjson==3.10.16 ; extra == "app"
Requires-Dist: packaging==24.2 ; extra == "app"
Requires-Dist: pandocfilters==1.5.1 ; extra == "app"
Requires-Dist: parso==0.8.4 ; extra == "app"
Requires-Dist: pathspec==0.12.1 ; extra == "app"
Requires-Dist: pexpect==4.9.0 ; extra == "app"
Requires-Dist: pillow==11.3.0 ; extra == "app"
Requires-Dist: platformdirs==4.3.7 ; extra == "app"
Requires-Dist: polars==1.12.0 ; extra == "app"
Requires-Dist: prompt-toolkit==3.0.51 ; extra == "app"
Requires-Dist: psutil==7.0.0 ; extra == "app"
Requires-Dist: ptyprocess==0.7.0 ; extra == "app"
Requires-Dist: pure-eval==0.2.3 ; extra == "app"
Requires-Dist: pyarrow==19.0.1 ; extra == "app"
Requires-Dist: pygments==2.19.1 ; extra == "app"
Requires-Dist: pyparsing==3.2.3 ; extra == "app"
Requires-Dist: python-dateutil==2.9.0.post0 ; extra == "app"
Requires-Dist: python-multipart==0.0.20 ; extra == "app"
Requires-Dist: pyyaml==6.0.2 ; extra == "app"
Requires-Dist: pyzmq==26.4.0 ; extra == "app"
Requires-Dist: questionary==2.1.0 ; extra == "app"
Requires-Dist: randomgen==2.1.1 ; extra == "app"
Requires-Dist: referencing==0.36.2 ; extra == "app"
Requires-Dist: requests==2.32.4 ; extra == "app"
Requires-Dist: rpds-py==0.24.0 ; extra == "app"
Requires-Dist: scikit-learn==1.6.1 ; extra == "app"
Requires-Dist: scipy==1.15.2 ; extra == "app"
Requires-Dist: shiny==1.4.0 ; extra == "app"
Requires-Dist: six==1.17.0 ; extra == "app"
Requires-Dist: sniffio==1.3.1 ; extra == "app"
Requires-Dist: soupsieve==2.6 ; extra == "app"
Requires-Dist: stack-data==0.6.3 ; extra == "app"
Requires-Dist: starlette==0.47.2 ; extra == "app"
Requires-Dist: threadpoolctl==3.6.0 ; extra == "app"
Requires-Dist: tinycss2==1.4.0 ; extra == "app"
Requires-Dist: tomli==2.2.1 ; extra == "app"
Requires-Dist: tornado==6.5.1 ; extra == "app"
Requires-Dist: traitlets==5.14.3 ; extra == "app"
Requires-Dist: typing-extensions==4.13.2 ; extra == "app"
Requires-Dist: uc-micro-py==1.0.3 ; extra == "app"
Requires-Dist: urllib3==2.5.0 ; extra == "app"
Requires-Dist: uvicorn==0.34.1 ; extra == "app"
Requires-Dist: watchfiles==1.0.5 ; extra == "app"
Requires-Dist: wcwidth==0.2.13 ; extra == "app"
Requires-Dist: webencodings==0.5.1 ; extra == "app"
Requires-Dist: websockets==15.0.1 ; extra == "app"
Requires-Dist: wrapt==1.17.2 ; extra == "app"
Project-URL: Home, https://github.com/opendp/dp-wizard
Provides-Extra: app

# DP Wizard

[![pypi](https://img.shields.io/pypi/v/dp_wizard)](https://pypi.org/project/dp_wizard/)

DP Wizard makes it easier to get started with differential privacy.

You can run DP Wizard locally and upload your own CSV,
or use the [cloud deployment](https://mccalluc-dp-wizard.share.connect.posit.cloud/) and only provide column names to protect your private data.
In either case, you'll be prompted to describe your privacy budget and the analysis you need, including:

- Grouping
- DP means, medians, and histograms

With that information, DP Wizard provides

- A Jupyter notebook which demonstrates how to use the [OpenDP Library](https://docs.opendp.org/).
- A plain Python script.
- Text and CSV reports.

## Usage

DP Wizard requires Python 3.10 or later.
You can check your current version with `python --version`.
The exact upgrade process will depend on your environment and operating system.

Install with `pip install 'dp_wizard[app]'` and you can start DP Wizard from the command line.

```
usage: dp-wizard [-h] [--sample | --cloud]

DP Wizard makes it easier to get started with Differential Privacy.

options:
  -h, --help  show this help message and exit
  --sample    Generate a sample CSV: See how DP Wizard works without providing
              your own data
  --cloud     Prompt for column names instead of CSV upload

Unless you have set "--sample" or "--cloud", you will specify a CSV
inside the application.

Provide a "Private CSV" if you only have a private data set, and want to
make a release from it: The preview visualizations will only use
simulated data, and apart from the headers, the private CSV is not
read until the release.

Provide a "Public CSV" if you have a public data set, and are curious how
DP can be applied: The preview visualizations will use your public data.

Provide both if you have two CSVs with the same structure.
Perhaps the public CSV is older and no longer sensitive. Preview
visualizations will be made with the public data, but the release will
be made with private data.
```

