solarwindpy 0.0.1.dev0__py3-none-any.whl → 0.1.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of solarwindpy might be problematic. Click here for more details.
- plans/.velocity/metrics.json +96 -0
- plans/0-overview-template.md +268 -0
- plans/N-phase-template.md +106 -0
- plans/PLAN_AUDIT_SUMMARY.md +173 -0
- plans/TEMPLATE-USAGE-GUIDE.md +198 -0
- plans/__init__.py +1 -0
- plans/abandoned/compaction-agent-system/0-Overview.md +123 -0
- plans/abandoned/compaction-agent-system/agents-index-update-plan.md +109 -0
- plans/abandoned/compaction-agent-system/compacted_state.md +85 -0
- plans/abandoned/compaction-agent-system/implementation-plan.md +107 -0
- plans/abandoned/compaction-agent-system/system-validation-report.md +159 -0
- plans/abandoned/compaction-agent-system/usage-guide.md +210 -0
- plans/abandoned/hook-system-enhancement/0-Overview.md +214 -0
- plans/abandoned/hook-system-enhancement/1-Phase1-Core-Infrastructure.md +313 -0
- plans/abandoned/hook-system-enhancement/2-Phase2-Intelligent-Testing.md +385 -0
- plans/abandoned/hook-system-enhancement/3-Phase3-Physics-Validation.md +444 -0
- plans/abandoned/hook-system-enhancement/4-Phase4-Performance-Monitoring.md +458 -0
- plans/abandoned/hook-system-enhancement/5-Phase5-Developer-Experience.md +532 -0
- plans/abandoned/hook-system-enhancement/6-Implementation-Timeline.md +274 -0
- plans/abandoned/hook-system-enhancement/7-Risk-Management.md +376 -0
- plans/abandoned/hook-system-enhancement/8-Testing-Strategy.md +579 -0
- plans/abandoned/readthedocs-automation/0-Overview.md +247 -0
- plans/abandoned/readthedocs-automation/1-Emergency-Documentation-Fixes.md +270 -0
- plans/abandoned/readthedocs-automation/2-Template-System-Enhancement.md +811 -0
- plans/abandoned/readthedocs-automation/3-Quality-Audit-ReadTheDocs-Integration.md +844 -0
- plans/abandoned/readthedocs-automation/4-Plan-Consolidation-Cleanup.md +632 -0
- plans/abandoned/readthedocs-automation/9-Closeout.md +207 -0
- plans/abandoned/readthedocs-automation/ABANDONMENT_REASON.md +72 -0
- plans/cicd-architecture-redesign/0-Overview.md +193 -0
- plans/cicd-architecture-redesign/1-Workflow-Creation.md +103 -0
- plans/cicd-architecture-redesign/2-Version-Detection.md +123 -0
- plans/cicd-architecture-redesign/3-Deployment-Gates.md +169 -0
- plans/cicd-architecture-redesign/4-RC-Testing.md +194 -0
- plans/cicd-architecture-redesign/5-TestPyPI-Validation.md +264 -0
- plans/cicd-architecture-redesign/6-Production-Release.md +263 -0
- plans/cicd-architecture-redesign/7-Cleanup.md +243 -0
- plans/cicd-architecture-redesign/8-Documentation.md +285 -0
- plans/cicd-architecture-redesign/Closeout.md +225 -0
- plans/closeout-template.md +259 -0
- plans/completed/circular-import-audit/0-Overview.md +152 -0
- plans/completed/circular-import-audit/1-Static-Dependency-Analysis.md +62 -0
- plans/completed/circular-import-audit/2-Dynamic-Import-Testing.md +56 -0
- plans/completed/circular-import-audit/3-Performance-Impact-Assessment.md +56 -0
- plans/completed/circular-import-audit/4-Issue-Remediation.md +78 -0
- plans/completed/circular-import-audit/5-Preventive-Infrastructure.md +89 -0
- plans/completed/claude-settings-ecosystem-alignment/0-Overview.md +162 -0
- plans/completed/claude-settings-ecosystem-alignment/1-Security-Foundation.md +148 -0
- plans/completed/claude-settings-ecosystem-alignment/2-Hook-Integration.md +158 -0
- plans/completed/claude-settings-ecosystem-alignment/3-Agent-System-Integration.md +177 -0
- plans/completed/claude-settings-ecosystem-alignment/4-Enhanced-Workflow-Automation.md +159 -0
- plans/completed/claude-settings-ecosystem-alignment/5-Validation-Monitoring.md +181 -0
- plans/completed/claude-settings-ecosystem-alignment/compacted_session_state.md +290 -0
- plans/completed/combined_plan_with_checklist_documentation/1-Overview-and-Goals.md +51 -0
- plans/completed/combined_plan_with_checklist_documentation/2-Toolchain-and-Hosting.md +69 -0
- plans/completed/combined_plan_with_checklist_documentation/3-Repository-Structure.md +61 -0
- plans/completed/combined_plan_with_checklist_documentation/4-Configuration-and-Standards.md +70 -0
- plans/completed/combined_plan_with_checklist_documentation/5-Documentation-Content.md +62 -0
- plans/completed/combined_plan_with_checklist_documentation/6-CI-CD-and-Validation.md +58 -0
- plans/completed/combined_plan_with_checklist_documentation/7-Maintenance.md +55 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/0-Overview.md +135 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/1-Common-fixtures.md +59 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/10-power_laws.md +56 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/2-core.py-FitFunction.md +118 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/3-gaussians.py-Gaussian-GaussianNormalized-GaussianLn.md +69 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/4-trend_fits.py-TrendFit.md +99 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/5-plots.py-FFPlot.md +98 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/6-tex_info.py-TeXinfo.md +79 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/7-Justification.md +49 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/8-exponentials.md +64 -0
- plans/completed/combined_test_plan_with_checklist_fitfunctions/9-lines.md +58 -0
- plans/completed/combined_test_plan_with_checklist_plotting/0-Overview.md +142 -0
- plans/completed/combined_test_plan_with_checklist_plotting/1-base.py.md +90 -0
- plans/completed/combined_test_plan_with_checklist_plotting/10-labels-special.py.md +102 -0
- plans/completed/combined_test_plan_with_checklist_plotting/11-labels-chemistry.py.md +212 -0
- plans/completed/combined_test_plan_with_checklist_plotting/12-labels-composition.py.md +242 -0
- plans/completed/combined_test_plan_with_checklist_plotting/13-labels-datetime.py.md +247 -0
- plans/completed/combined_test_plan_with_checklist_plotting/14-labels-elemental_abundance.py.md +274 -0
- plans/completed/combined_test_plan_with_checklist_plotting/15-visual-validation.md +256 -0
- plans/completed/combined_test_plan_with_checklist_plotting/16-integration-testing.md +266 -0
- plans/completed/combined_test_plan_with_checklist_plotting/17-performance-benchmarks.md +267 -0
- plans/completed/combined_test_plan_with_checklist_plotting/18-Fixtures-and-Utilities.md +86 -0
- plans/completed/combined_test_plan_with_checklist_plotting/2-agg_plot.py.md +90 -0
- plans/completed/combined_test_plan_with_checklist_plotting/3-histograms.py.md +201 -0
- plans/completed/combined_test_plan_with_checklist_plotting/4-scatter.py.md +167 -0
- plans/completed/combined_test_plan_with_checklist_plotting/5-spiral.py.md +216 -0
- plans/completed/combined_test_plan_with_checklist_plotting/6-orbits.py.md +108 -0
- plans/completed/combined_test_plan_with_checklist_plotting/7-tools.py.md +86 -0
- plans/completed/combined_test_plan_with_checklist_plotting/8-select_data_from_figure.py.md +97 -0
- plans/completed/combined_test_plan_with_checklist_plotting/9-labels-base.py.md +88 -0
- plans/completed/combined_test_plan_with_checklist_solar_activity/.gitkeep +0 -0
- plans/completed/combined_test_plan_with_checklist_solar_activity/0-Overview.md +170 -0
- plans/completed/combined_test_plan_with_checklist_solar_activity/1-Package-Entry-Point-__init__.py.md +121 -0
- plans/completed/combined_test_plan_with_checklist_solar_activity/2-Core-Base-Classes-base.py.md +142 -0
- plans/completed/combined_test_plan_with_checklist_solar_activity/3-Plotting-Helpers-plots.py.md +123 -0
- plans/completed/combined_test_plan_with_checklist_solar_activity/4-LISIRD-Sub-package.md +119 -0
- plans/completed/combined_test_plan_with_checklist_solar_activity/5-Extrema-Calculator.md +103 -0
- plans/completed/combined_test_plan_with_checklist_solar_activity/6-Sunspot-Number-Sub-package.md +163 -0
- plans/completed/combined_test_plan_with_checklist_solar_activity/7-Sunspot-Number-Init.py.md +217 -0
- plans/completed/combined_test_plan_with_checklist_solar_activity/compacted_state.md +52 -0
- plans/completed/compaction-agent-modernization/0-Overview.md +156 -0
- plans/completed/compaction-agent-modernization/1-Architecture-Audit-Gap-Analysis.md +132 -0
- plans/completed/compaction-agent-modernization/2-Token-Baseline-Recalibration.md +153 -0
- plans/completed/compaction-agent-modernization/3-Agent-Reference-Updates.md +184 -0
- plans/completed/compaction-agent-modernization/4-Compression-Algorithm-Modernization.md +238 -0
- plans/completed/compaction-agent-modernization/5-Workflow-Integration-Streamlining.md +252 -0
- plans/completed/compaction-agent-modernization/6-Template-Structure-Optimization.md +240 -0
- plans/completed/compaction-agent-modernization/7-Integration-Testing-Validation.md +292 -0
- plans/completed/compaction-hook-enhancement/0-Overview.md +150 -0
- plans/completed/compaction-hook-enhancement/1-Token-Estimation-Enhancement.md +179 -0
- plans/completed/compaction-hook-enhancement/2-Compression-Intelligence.md +294 -0
- plans/completed/compaction-hook-enhancement/3-Git-Integration-Metadata.md +310 -0
- plans/completed/compaction-hook-enhancement/4-Session-Continuity-Features.md +358 -0
- plans/completed/compaction-hook-enhancement/5-Testing-Strategy.md +404 -0
- plans/completed/compaction-hook-enhancement/6-Integration-Roadmap.md +319 -0
- plans/completed/compaction-hook-enhancement/compacted_state.md +142 -0
- plans/completed/docstring-audit-enhancement/0-Overview.md +274 -0
- plans/completed/docstring-audit-enhancement/1-Infrastructure-Setup-and-Validation-Tools.md +206 -0
- plans/completed/docstring-audit-enhancement/2-Core-Physics-Modules-Enhancement.md +237 -0
- plans/completed/docstring-audit-enhancement/3-Fitfunctions-Mathematical-Modules-Enhancement.md +188 -0
- plans/completed/docstring-audit-enhancement/4-Plotting-Visualization-Modules-Enhancement.md +243 -0
- plans/completed/docstring-audit-enhancement/5-Specialized-Modules-Enhancement.md +216 -0
- plans/completed/docstring-audit-enhancement/6-Validation-and-Integration.md +216 -0
- plans/completed/fitfunctions-testing-implementation/0-Overview.md +130 -0
- plans/completed/fitfunctions-testing-implementation/1-Test-Infrastructure-Setup.md +79 -0
- plans/completed/fitfunctions-testing-implementation/2-Common-Fixtures-Test-Utilities.md +104 -0
- plans/completed/fitfunctions-testing-implementation/3-Core-FitFunction-Testing.md +168 -0
- plans/completed/fitfunctions-testing-implementation/4-Specialized-Function-Classes.md +210 -0
- plans/completed/fitfunctions-testing-implementation/5-Advanced-Classes-Testing.md +214 -0
- plans/completed/fitfunctions-testing-implementation/6-Plotting-Integration-Testing.md +231 -0
- plans/completed/fitfunctions-testing-implementation/7-Extended-Coverage-BONUS.md +184 -0
- plans/completed/numpy-docstring-conversion-plan/numpy-docstring-conversion-plan.md +118 -0
- plans/completed/pr-review-remediation/0-Overview.md +138 -0
- plans/completed/pr-review-remediation/1-Critical-Safety-Improvements.md +179 -0
- plans/completed/pr-review-remediation/2-Smart-Timeouts-Validation.md +399 -0
- plans/completed/pr-review-remediation/3-Enhanced-GitHub-Integration.md +258 -0
- plans/completed/pr-review-remediation/compacted_state.md +66 -0
- plans/completed/python-310-migration/0-Overview.md +390 -0
- plans/completed/python-310-migration/1-Planning-Setup.md +164 -0
- plans/completed/python-310-migration/2-Implementation.md +256 -0
- plans/completed/python-310-migration/3-Testing-Validation.md +335 -0
- plans/completed/python-310-migration/4-Documentation-Release.md +274 -0
- plans/completed/python-310-migration/5-Closeout.md +252 -0
- plans/completed/requirements-management-consolidation/0-Overview.md +118 -0
- plans/completed/requirements-management-consolidation/1-Documentation-Validation-Environment-Setup.md +116 -0
- plans/completed/requirements-management-consolidation/2-Requirements-Consolidation.md +161 -0
- plans/completed/requirements-management-consolidation/3-Workflow-Automation-Final-Integration.md +196 -0
- plans/completed/single-ecosystem-plan-implementation/0-Overview.md +83 -0
- plans/completed/single-ecosystem-plan-implementation/1-Plan-Preservation-Session-Management.md +38 -0
- plans/completed/single-ecosystem-plan-implementation/2-File-Structure-Optimization.md +43 -0
- plans/completed/single-ecosystem-plan-implementation/3-Plan-Migration-Archive-Setup.md +82 -0
- plans/completed/single-ecosystem-plan-implementation/4-Agent-System-Transformation.md +108 -0
- plans/completed/single-ecosystem-plan-implementation/5-Template-System-Enhancement.md +131 -0
- plans/completed/single-ecosystem-plan-implementation/6-Final-Validation-Testing.md +120 -0
- plans/completed/test-directory-consolidation/0-Overview.md +51 -0
- plans/completed/test-directory-consolidation/1-Structure-Preparation.md +82 -0
- plans/completed/test-directory-consolidation/2-File-Migration.md +100 -0
- plans/completed/test-directory-consolidation/3-Import-Transformation.md +117 -0
- plans/completed/test-directory-consolidation/4-Configuration-Consolidation.md +140 -0
- plans/completed/test-directory-consolidation/5-Validation.md +152 -0
- plans/completed/test-directory-consolidation/6-Cleanup.md +156 -0
- plans/completed/test-planning-agents-architecture/0-Overview.md +79 -0
- plans/completed/test-planning-agents-architecture/1-Branch-Isolation-Testing.md +49 -0
- plans/completed/test-planning-agents-architecture/2-Cross-Branch-Coordination.md +51 -0
- plans/completed/test-planning-agents-architecture/3-Merge-Workflow-Testing.md +48 -0
- plans/deployment-semver-pypi-rtd/0-Overview.md +463 -0
- plans/deployment-semver-pypi-rtd/1-Semantic-Versioning-Foundation.md +136 -0
- plans/deployment-semver-pypi-rtd/2-PyPI-Deployment-Infrastructure.md +168 -0
- plans/deployment-semver-pypi-rtd/3-Release-Automation.md +214 -0
- plans/deployment-semver-pypi-rtd/4-Plan-Closeout.md +543 -0
- plans/deployment-semver-pypi-rtd/compacted_session_state.md +172 -0
- plans/deployment-semver-pypi-rtd/compacted_state.md +131 -0
- plans/documentation-code-audit/0-Overview.md +393 -0
- plans/documentation-code-audit/1-Discovery-Inventory.md +183 -0
- plans/documentation-code-audit/2-Execution-Environment-Setup.md +263 -0
- plans/documentation-code-audit/3-Systematic-Validation.md +322 -0
- plans/documentation-code-audit/4-Code-Example-Remediation.md +358 -0
- plans/documentation-code-audit/5-Physics-MultiIndex-Compliance.md +464 -0
- plans/documentation-code-audit/6-Doctest-Integration.md +523 -0
- plans/documentation-code-audit/7-Reporting-Documentation.md +498 -0
- plans/documentation-code-audit/8-Closeout.md +456 -0
- plans/documentation-rebuild-session/compacted_state.md +109 -0
- plans/documentation-rendering-fixes/0-Overview.md +104 -0
- plans/documentation-rendering-fixes/1-Sphinx-Build-Diagnostics-Warning-Audit.md +101 -0
- plans/documentation-rendering-fixes/2-Configuration-Infrastructure-Fixes.md +113 -0
- plans/documentation-rendering-fixes/3-Docstring-Syntax-Audit-Repair.md +131 -0
- plans/documentation-rendering-fixes/4-HTML-Page-Rendering-Verification.md +113 -0
- plans/documentation-rendering-fixes/5-Advanced-Documentation-Quality-Assurance.md +119 -0
- plans/documentation-rendering-fixes/6-Documentation-Build-Optimization-Testing.md +129 -0
- plans/documentation-rendering-fixes/compacted_state.md +132 -0
- plans/documentation-template-fix/0-Overview.md +197 -0
- plans/documentation-template-fix/1-Template-System-Analysis.md +269 -0
- plans/documentation-template-fix/2-Template-Modification.md +609 -0
- plans/documentation-template-fix/3-Build-System-Integration.md +766 -0
- plans/documentation-template-fix/4-Testing-Validation.md +1399 -0
- plans/documentation-template-fix/5-Documentation-Training.md +602 -0
- plans/documentation-workflow-fix/0-Overview.md +222 -0
- plans/documentation-workflow-fix/1-Immediate-Fixes.md +238 -0
- plans/documentation-workflow-fix/2-Configuration-Setup.md +298 -0
- plans/documentation-workflow-fix/3-Pre-commit-Integration.md +382 -0
- plans/documentation-workflow-fix/4-Workflow-Improvements.md +446 -0
- plans/documentation-workflow-fix/5-Documentation-and-Training.md +527 -0
- plans/duplicate-object-warnings-fix-plan.md +130 -0
- plans/github-issues-migration/0-Overview.md +510 -0
- plans/github-issues-migration/1-Foundation-Label-System.md +180 -0
- plans/github-issues-migration/2-Migration-Tool-Rewrite.md +235 -0
- plans/github-issues-migration/3-CLI-Integration-Automation.md +169 -0
- plans/github-issues-migration/4-Validated-Migration.md +252 -0
- plans/github-issues-migration/5-Documentation-Training.md +171 -0
- plans/github-issues-migration/6-Closeout.md +179 -0
- plans/github-workflows-repair/repair-plan.md +299 -0
- plans/issues_from_plans.py +342 -0
- plans/pr-270-doc-validation-fixes/0-Overview.md +354 -0
- plans/pr-270-doc-validation-fixes/1-Critical-PR-Fixes.md +117 -0
- plans/pr-270-doc-validation-fixes/2-Framework-Right-Sizing.md +129 -0
- plans/pr-270-doc-validation-fixes/3-Sustainable-Documentation.md +126 -0
- plans/pr-270-doc-validation-fixes/4-Closeout-Migration.md +143 -0
- plans/pr-270-doc-validation-fixes/PLAN_COMPLETED.md +149 -0
- plans/python-310-migration/0-Overview.md +390 -0
- plans/python-310-migration/1-Planning-Setup.md +164 -0
- plans/python-310-migration/2-Implementation.md +256 -0
- plans/python-310-migration/3-Testing-Validation.md +335 -0
- plans/python-310-migration/4-Documentation-Release.md +274 -0
- plans/python-310-migration/5-Closeout.md +252 -0
- plans/readthedocs-simplified/0-Overview.md +243 -0
- plans/readthedocs-simplified/1-Immediate-Fixes.md +216 -0
- plans/readthedocs-simplified/2-Template-Simplification.md +278 -0
- plans/readthedocs-simplified/3-ReadTheDocs-Setup.md +298 -0
- plans/readthedocs-simplified/4-Testing-Validation.md +328 -0
- plans/readthedocs-simplified/5-Closeout.md +231 -0
- plans/readthedocs-simplified/compacted_state.md +127 -0
- plans/session-compaction-2025-08-12/compacted_state.md +114 -0
- plans/session-compaction-2025-08-13/compacted_state.md +145 -0
- plans/session-continuity-protocol/0-Overview.md +35 -0
- plans/session-continuity-protocol/1-Core-Principles-Framework.md +40 -0
- plans/session-continuity-protocol/2-Pre-Session-Validation-System.md +79 -0
- plans/session-continuity-protocol/3-Context-Switching-Prevention.md +87 -0
- plans/session-continuity-protocol/4-Progress-Tracking-Recovery.md +100 -0
- plans/sphinx-warnings-analysis.md +222 -0
- plans/systemprompt-optimization/0-Overview.md +447 -0
- plans/systemprompt-optimization/1-Deploy-SystemPrompt.md +114 -0
- plans/systemprompt-optimization/2-Documentation-Alignment.md +198 -0
- plans/systemprompt-optimization/3-Monitoring-Infrastructure.md +396 -0
- plans/systemprompt-optimization/4-Implementation-Script.md +450 -0
- plans/systemprompt-optimization/9-Closeout.md +165 -0
- plans/systemprompt-optimization/compacted_state.md +143 -0
- plans/template-value-propositions/0-Overview.md +357 -0
- plans/template-value-propositions/1-Value-Proposition-Framework-Design.md +144 -0
- plans/template-value-propositions/2-Plan-Template-Enhancement.md +178 -0
- plans/template-value-propositions/3-Value-Generator-Hook-Implementation.md +291 -0
- plans/template-value-propositions/4-Value-Validator-Hook-Implementation.md +274 -0
- plans/template-value-propositions/5-Documentation-Agent-Updates.md +219 -0
- plans/template-value-propositions/6-Integration-Testing-Validation.md +247 -0
- plans/tests-audit/0-Overview.md +410 -0
- plans/tests-audit/1-Discovery-Inventory.md +170 -0
- plans/tests-audit/2-Physics-Validation-Audit.md +195 -0
- plans/tests-audit/3-Architecture-Compliance.md +195 -0
- plans/tests-audit/4-Numerical-Stability-Analysis.md +203 -0
- plans/tests-audit/5-Documentation-Enhancement.md +220 -0
- plans/tests-audit/6-Audit-Deliverables.md +220 -0
- plans/tests-audit/7-Closeout.md +252 -0
- plans/tests-audit/artifacts/ARCHITECTURE_COMPLIANCE_REPORT.md +315 -0
- plans/tests-audit/artifacts/ARCHITECTURE_RECOMMENDATIONS.md +943 -0
- plans/tests-audit/artifacts/COMPREHENSIVE_AUDIT_REPORT.md +356 -0
- plans/tests-audit/artifacts/CONTRIBUTING_ENHANCED_TEMPLATE.md +419 -0
- plans/tests-audit/artifacts/COVERAGE_GAP_ANALYSIS.md +152 -0
- plans/tests-audit/artifacts/DOCUMENTATION_ENHANCEMENT_REPORT.md +502 -0
- plans/tests-audit/artifacts/EXECUTIVE_AUDIT_SUMMARY.md +129 -0
- plans/tests-audit/artifacts/IMPLEMENTATION_ROADMAP.md +647 -0
- plans/tests-audit/artifacts/NUMERICAL_RECOMMENDATIONS.md +739 -0
- plans/tests-audit/artifacts/NUMERICAL_STABILITY_GUIDE_TEMPLATE.rst +451 -0
- plans/tests-audit/artifacts/NUMERICAL_STABILITY_REPORT.md +301 -0
- plans/tests-audit/artifacts/PHASE_3_SUMMARY.md +280 -0
- plans/tests-audit/artifacts/PHASE_4_SUMMARY.md +229 -0
- plans/tests-audit/artifacts/PHASE_5_SUMMARY.md +292 -0
- plans/tests-audit/artifacts/PHASE_6_CLOSEOUT.md +278 -0
- plans/tests-audit/artifacts/PHYSICS_GUIDE_TEMPLATE.rst +268 -0
- plans/tests-audit/artifacts/PHYSICS_VALIDATION_REPORT.md +235 -0
- plans/tests-audit/artifacts/TECHNICAL_DELIVERABLES_PACKAGE.md +2502 -0
- plans/tests-audit/artifacts/TEST_INVENTORY.csv +1204 -0
- plans/tests-audit/artifacts/TEST_INVENTORY.md +135 -0
- plans/tests-audit/artifacts/test_discovery_analysis.py +231 -0
- plans/tests-audit/artifacts/test_parser.py +395 -0
- solarwindpy/README.md +3 -0
- solarwindpy/Untitled.ipynb +54 -0
- solarwindpy/__init__.py +74 -0
- solarwindpy/core/__init__.py +23 -0
- solarwindpy/core/alfvenic_turbulence.py +804 -0
- solarwindpy/core/base.py +267 -0
- solarwindpy/core/ions.py +309 -0
- solarwindpy/core/plasma.py +2133 -0
- solarwindpy/core/spacecraft.py +256 -0
- solarwindpy/core/tensor.py +90 -0
- solarwindpy/core/units_constants.py +199 -0
- solarwindpy/core/vector.py +328 -0
- solarwindpy/fitfunctions/__init__.py +20 -0
- solarwindpy/fitfunctions/core.py +734 -0
- solarwindpy/fitfunctions/exponentials.py +188 -0
- solarwindpy/fitfunctions/gaussians.py +264 -0
- solarwindpy/fitfunctions/lines.py +116 -0
- solarwindpy/fitfunctions/moyal.py +71 -0
- solarwindpy/fitfunctions/plots.py +751 -0
- solarwindpy/fitfunctions/power_laws.py +209 -0
- solarwindpy/fitfunctions/tex_info.py +568 -0
- solarwindpy/fitfunctions/trend_fits.py +482 -0
- solarwindpy/instabilities/__init__.py +16 -0
- solarwindpy/instabilities/beta_ani.py +82 -0
- solarwindpy/instabilities/verscharen2016.py +631 -0
- solarwindpy/plotting/__init__.py +33 -0
- solarwindpy/plotting/agg_plot.py +489 -0
- solarwindpy/plotting/base.py +465 -0
- solarwindpy/plotting/hist1d.py +405 -0
- solarwindpy/plotting/hist2d.py +1035 -0
- solarwindpy/plotting/histograms.py +1845 -0
- solarwindpy/plotting/labels/__init__.py +104 -0
- solarwindpy/plotting/labels/base.py +686 -0
- solarwindpy/plotting/labels/chemistry.py +19 -0
- solarwindpy/plotting/labels/composition.py +100 -0
- solarwindpy/plotting/labels/datetime.py +235 -0
- solarwindpy/plotting/labels/elemental_abundance.py +73 -0
- solarwindpy/plotting/labels/special.py +794 -0
- solarwindpy/plotting/orbits.py +515 -0
- solarwindpy/plotting/scatter.py +99 -0
- solarwindpy/plotting/select_data_from_figure.py +329 -0
- solarwindpy/plotting/spiral.py +980 -0
- solarwindpy/plotting/tools.py +434 -0
- solarwindpy/scripts/__init__.py +1 -0
- solarwindpy/scripts/logs/.gitignore +1 -0
- solarwindpy/solar_activity/__init__.py +53 -0
- solarwindpy/solar_activity/base.py +605 -0
- solarwindpy/solar_activity/lisird/__init__.py +3 -0
- solarwindpy/solar_activity/lisird/extrema_calculator.py +394 -0
- solarwindpy/solar_activity/lisird/lisird.py +319 -0
- solarwindpy/solar_activity/plots.py +116 -0
- solarwindpy/solar_activity/sunspot_number/.DS_Store +0 -0
- solarwindpy/solar_activity/sunspot_number/__init__.py +3 -0
- solarwindpy/solar_activity/sunspot_number/sidc.py +556 -0
- solarwindpy/solar_activity/sunspot_number/ssn_extrema.csv +72 -0
- solarwindpy/solar_activity/sunspot_number/ssn_extrema.csv.silso +72 -0
- solarwindpy/tools/__init__.py +162 -0
- solarwindpy-0.1.0.dist-info/METADATA +181 -0
- solarwindpy-0.1.0.dist-info/RECORD +409 -0
- {solarwindpy-0.0.1.dev0.dist-info → solarwindpy-0.1.0.dist-info}/WHEEL +1 -1
- solarwindpy-0.1.0.dist-info/licenses/LICENSE.rst +32 -0
- solarwindpy-0.1.0.dist-info/top_level.txt +3 -0
- tests/__init__.py +1 -0
- tests/conftest.py +10 -0
- tests/core/__init__.py +1 -0
- tests/core/test_alfvenic_turbulence.py +544 -0
- tests/core/test_base.py +112 -0
- tests/core/test_base_head_tail.py +29 -0
- tests/core/test_base_mi_tuples.py +11 -0
- tests/core/test_core_verify_datetimeindex.py +32 -0
- tests/core/test_ions.py +325 -0
- tests/core/test_plasma.py +2581 -0
- tests/core/test_plasma_io.py +12 -0
- tests/core/test_quantities.py +507 -0
- tests/core/test_spacecraft.py +210 -0
- tests/core/test_units_constants.py +22 -0
- tests/data/epoch.csv +4 -0
- tests/data/plasma.csv +4 -0
- tests/data/spacecraft.csv +4 -0
- tests/fitfunctions/conftest.py +60 -0
- tests/fitfunctions/test_core.py +193 -0
- tests/fitfunctions/test_exponentials.py +342 -0
- tests/fitfunctions/test_gaussians.py +142 -0
- tests/fitfunctions/test_lines.py +349 -0
- tests/fitfunctions/test_moyal.py +258 -0
- tests/fitfunctions/test_plots.py +258 -0
- tests/fitfunctions/test_power_laws.py +365 -0
- tests/fitfunctions/test_tex_info.py +183 -0
- tests/fitfunctions/test_trend_fit_properties.py +31 -0
- tests/fitfunctions/test_trend_fits.py +244 -0
- tests/plotting/__init__.py +1 -0
- tests/plotting/labels/__init__.py +1 -0
- tests/plotting/labels/test_chemistry.py +243 -0
- tests/plotting/labels/test_composition.py +345 -0
- tests/plotting/labels/test_datetime.py +445 -0
- tests/plotting/labels/test_elemental_abundance.py +366 -0
- tests/plotting/labels/test_init.py +66 -0
- tests/plotting/labels/test_labels_base.py +347 -0
- tests/plotting/labels/test_special.py +550 -0
- tests/plotting/test_agg_plot.py +602 -0
- tests/plotting/test_base.py +752 -0
- tests/plotting/test_fixtures_utilities.py +775 -0
- tests/plotting/test_histograms.py +546 -0
- tests/plotting/test_integration.py +675 -0
- tests/plotting/test_orbits.py +435 -0
- tests/plotting/test_performance.py +708 -0
- tests/plotting/test_scatter.py +752 -0
- tests/plotting/test_select_data_from_figure.py +1209 -0
- tests/plotting/test_spiral.py +573 -0
- tests/plotting/test_tools.py +607 -0
- tests/plotting/test_visual_validation.py +465 -0
- tests/solar_activity/__init__.py +1 -0
- tests/solar_activity/lisird/__init__.py +1 -0
- tests/solar_activity/lisird/test_extrema_calculator.py +593 -0
- tests/solar_activity/lisird/test_lisird_id.py +187 -0
- tests/solar_activity/sunspot_number/__init__.py +1 -0
- tests/solar_activity/sunspot_number/test_init.py +399 -0
- tests/solar_activity/sunspot_number/test_sidc.py +465 -0
- tests/solar_activity/sunspot_number/test_sidc_id.py +223 -0
- tests/solar_activity/sunspot_number/test_sidc_loader.py +275 -0
- tests/solar_activity/sunspot_number/test_ssn_extrema.py +406 -0
- tests/solar_activity/test_base.py +656 -0
- tests/solar_activity/test_init.py +396 -0
- tests/solar_activity/test_plots.py +371 -0
- tests/test_circular_imports.py +408 -0
- tests/test_issue_titles.py +25 -0
- tests/test_statusline.py +298 -0
- solarwindpy-0.0.1.dev0.dist-info/METADATA +0 -14
- solarwindpy-0.0.1.dev0.dist-info/RECORD +0 -4
- solarwindpy-0.0.1.dev0.dist-info/top_level.txt +0 -1
|
@@ -0,0 +1,708 @@
|
|
|
1
|
+
"""Performance benchmarks for plotting functionality.
|
|
2
|
+
|
|
3
|
+
Tests performance characteristics and scalability of plotting operations with large
|
|
4
|
+
datasets typical in space physics applications.
|
|
5
|
+
"""
|
|
6
|
+
|
|
7
|
+
import pytest
|
|
8
|
+
import numpy as np
|
|
9
|
+
import pandas as pd
|
|
10
|
+
import matplotlib
|
|
11
|
+
import matplotlib.pyplot as plt
|
|
12
|
+
import time
|
|
13
|
+
import gc
|
|
14
|
+
import psutil
|
|
15
|
+
import os
|
|
16
|
+
import warnings
|
|
17
|
+
|
|
18
|
+
# Optional import for memory profiling
|
|
19
|
+
try:
|
|
20
|
+
from memory_profiler import profile
|
|
21
|
+
|
|
22
|
+
HAS_MEMORY_PROFILER = True
|
|
23
|
+
except ImportError:
|
|
24
|
+
HAS_MEMORY_PROFILER = False
|
|
25
|
+
|
|
26
|
+
def profile(func):
|
|
27
|
+
return func
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
# Configure matplotlib for testing
|
|
31
|
+
matplotlib.use("Agg")
|
|
32
|
+
plt.ioff()
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
class TestBasicPerformance:
|
|
36
|
+
"""Test basic performance characteristics of plotting operations."""
|
|
37
|
+
|
|
38
|
+
def setup_method(self):
|
|
39
|
+
"""Set up performance test environment."""
|
|
40
|
+
# Force garbage collection before tests
|
|
41
|
+
gc.collect()
|
|
42
|
+
self.process = psutil.Process(os.getpid())
|
|
43
|
+
|
|
44
|
+
def teardown_method(self):
|
|
45
|
+
"""Clean up after performance tests."""
|
|
46
|
+
plt.close("all")
|
|
47
|
+
gc.collect()
|
|
48
|
+
|
|
49
|
+
def get_memory_usage(self):
|
|
50
|
+
"""Get current memory usage in MB."""
|
|
51
|
+
return self.process.memory_info().rss / 1024 / 1024
|
|
52
|
+
|
|
53
|
+
def test_line_plot_performance(self):
|
|
54
|
+
"""Test line plot performance with various data sizes."""
|
|
55
|
+
data_sizes = [1000, 10000, 100000, 500000]
|
|
56
|
+
times = []
|
|
57
|
+
|
|
58
|
+
for size in data_sizes:
|
|
59
|
+
x = np.linspace(0, 10, size)
|
|
60
|
+
y = np.sin(x) + 0.1 * np.random.randn(size)
|
|
61
|
+
|
|
62
|
+
start_time = time.time()
|
|
63
|
+
|
|
64
|
+
fig, ax = plt.subplots()
|
|
65
|
+
ax.plot(x, y)
|
|
66
|
+
ax.set_xlabel("X")
|
|
67
|
+
ax.set_ylabel("Y")
|
|
68
|
+
ax.set_title(f"Line Plot - {size:,} points")
|
|
69
|
+
|
|
70
|
+
end_time = time.time()
|
|
71
|
+
elapsed = end_time - start_time
|
|
72
|
+
times.append(elapsed)
|
|
73
|
+
|
|
74
|
+
plt.close(fig)
|
|
75
|
+
|
|
76
|
+
# Performance assertions
|
|
77
|
+
if size <= 10000:
|
|
78
|
+
assert (
|
|
79
|
+
elapsed < 1.0
|
|
80
|
+
), f"Plot with {size} points took {elapsed:.3f}s (expected < 1.0s)"
|
|
81
|
+
elif size <= 100000:
|
|
82
|
+
assert (
|
|
83
|
+
elapsed < 5.0
|
|
84
|
+
), f"Plot with {size} points took {elapsed:.3f}s (expected < 5.0s)"
|
|
85
|
+
else:
|
|
86
|
+
assert (
|
|
87
|
+
elapsed < 15.0
|
|
88
|
+
), f"Plot with {size} points took {elapsed:.3f}s (expected < 15.0s)"
|
|
89
|
+
|
|
90
|
+
# Test that performance scales reasonably
|
|
91
|
+
assert len(times) == len(data_sizes)
|
|
92
|
+
print(f"Line plot timing: {list(zip(data_sizes, times))}")
|
|
93
|
+
|
|
94
|
+
def test_scatter_plot_performance(self):
|
|
95
|
+
"""Test scatter plot performance with various data sizes."""
|
|
96
|
+
data_sizes = [1000, 5000, 25000, 50000] # Smaller sizes for scatter
|
|
97
|
+
times = []
|
|
98
|
+
|
|
99
|
+
for size in data_sizes:
|
|
100
|
+
np.random.seed(42)
|
|
101
|
+
x = np.random.randn(size)
|
|
102
|
+
y = np.random.randn(size)
|
|
103
|
+
colors = np.random.rand(size)
|
|
104
|
+
|
|
105
|
+
start_time = time.time()
|
|
106
|
+
|
|
107
|
+
fig, ax = plt.subplots()
|
|
108
|
+
scatter = ax.scatter(x, y, c=colors, alpha=0.6, cmap="viridis")
|
|
109
|
+
ax.set_xlabel("X")
|
|
110
|
+
ax.set_ylabel("Y")
|
|
111
|
+
ax.set_title(f"Scatter Plot - {size:,} points")
|
|
112
|
+
plt.colorbar(scatter, ax=ax)
|
|
113
|
+
|
|
114
|
+
end_time = time.time()
|
|
115
|
+
elapsed = end_time - start_time
|
|
116
|
+
times.append(elapsed)
|
|
117
|
+
|
|
118
|
+
plt.close(fig)
|
|
119
|
+
|
|
120
|
+
# Performance assertions (scatter plots are slower)
|
|
121
|
+
if size <= 5000:
|
|
122
|
+
assert (
|
|
123
|
+
elapsed < 2.0
|
|
124
|
+
), f"Scatter with {size} points took {elapsed:.3f}s (expected < 2.0s)"
|
|
125
|
+
elif size <= 25000:
|
|
126
|
+
assert (
|
|
127
|
+
elapsed < 10.0
|
|
128
|
+
), f"Scatter with {size} points took {elapsed:.3f}s (expected < 10.0s)"
|
|
129
|
+
else:
|
|
130
|
+
assert (
|
|
131
|
+
elapsed < 30.0
|
|
132
|
+
), f"Scatter with {size} points took {elapsed:.3f}s (expected < 30.0s)"
|
|
133
|
+
|
|
134
|
+
print(f"Scatter plot timing: {list(zip(data_sizes, times))}")
|
|
135
|
+
|
|
136
|
+
def test_histogram_performance(self):
|
|
137
|
+
"""Test histogram performance with large datasets."""
|
|
138
|
+
data_sizes = [10000, 100000, 1000000]
|
|
139
|
+
bin_counts = [50, 100, 200]
|
|
140
|
+
|
|
141
|
+
for size in data_sizes:
|
|
142
|
+
for bins in bin_counts:
|
|
143
|
+
np.random.seed(42)
|
|
144
|
+
data = np.random.normal(0, 1, size)
|
|
145
|
+
|
|
146
|
+
start_time = time.time()
|
|
147
|
+
|
|
148
|
+
fig, ax = plt.subplots()
|
|
149
|
+
n, bins_out, patches = ax.hist(data, bins=bins, alpha=0.7, density=True)
|
|
150
|
+
ax.set_xlabel("Value")
|
|
151
|
+
ax.set_ylabel("Density")
|
|
152
|
+
ax.set_title(f"Histogram - {size:,} points, {bins} bins")
|
|
153
|
+
|
|
154
|
+
end_time = time.time()
|
|
155
|
+
elapsed = end_time - start_time
|
|
156
|
+
|
|
157
|
+
plt.close(fig)
|
|
158
|
+
|
|
159
|
+
# Histograms should be fast even for large data
|
|
160
|
+
assert (
|
|
161
|
+
elapsed < 5.0
|
|
162
|
+
), f"Histogram with {size} points, {bins} bins took {elapsed:.3f}s"
|
|
163
|
+
|
|
164
|
+
# Validate histogram output
|
|
165
|
+
assert len(n) == bins
|
|
166
|
+
assert len(patches) == bins
|
|
167
|
+
assert len(bins_out) == bins + 1
|
|
168
|
+
|
|
169
|
+
def test_memory_usage_scalability(self):
|
|
170
|
+
"""Test memory usage scaling with data size."""
|
|
171
|
+
initial_memory = self.get_memory_usage()
|
|
172
|
+
|
|
173
|
+
data_sizes = [10000, 50000, 100000]
|
|
174
|
+
memory_usages = []
|
|
175
|
+
|
|
176
|
+
for size in data_sizes:
|
|
177
|
+
# Clear memory before test
|
|
178
|
+
gc.collect()
|
|
179
|
+
mem_before = self.get_memory_usage()
|
|
180
|
+
|
|
181
|
+
# Create large dataset
|
|
182
|
+
x = np.linspace(0, 100, size)
|
|
183
|
+
y = np.sin(x) + 0.1 * np.random.randn(size)
|
|
184
|
+
|
|
185
|
+
fig, ax = plt.subplots(figsize=(12, 8))
|
|
186
|
+
ax.plot(x, y, linewidth=1)
|
|
187
|
+
ax.set_xlabel("X")
|
|
188
|
+
ax.set_ylabel("Y")
|
|
189
|
+
ax.set_title(f"Memory Test - {size:,} points")
|
|
190
|
+
ax.grid(True)
|
|
191
|
+
|
|
192
|
+
mem_after = self.get_memory_usage()
|
|
193
|
+
memory_increase = mem_after - mem_before
|
|
194
|
+
memory_usages.append(memory_increase)
|
|
195
|
+
|
|
196
|
+
plt.close(fig)
|
|
197
|
+
|
|
198
|
+
# Memory usage should be reasonable
|
|
199
|
+
assert (
|
|
200
|
+
memory_increase < 100
|
|
201
|
+
), f"Memory usage increased by {memory_increase:.1f}MB for {size} points"
|
|
202
|
+
|
|
203
|
+
print(f"Memory usage increases: {list(zip(data_sizes, memory_usages))}")
|
|
204
|
+
|
|
205
|
+
|
|
206
|
+
class TestAdvancedPerformance:
|
|
207
|
+
"""Test performance of advanced plotting features."""
|
|
208
|
+
|
|
209
|
+
def teardown_method(self):
|
|
210
|
+
"""Clean up after performance tests."""
|
|
211
|
+
plt.close("all")
|
|
212
|
+
gc.collect()
|
|
213
|
+
|
|
214
|
+
def test_contour_plot_performance(self):
|
|
215
|
+
"""Test contour plot performance with 2D data."""
|
|
216
|
+
grid_sizes = [50, 100, 200]
|
|
217
|
+
contour_levels = [10, 20, 50]
|
|
218
|
+
|
|
219
|
+
for grid_size in grid_sizes:
|
|
220
|
+
for levels in contour_levels:
|
|
221
|
+
x = np.linspace(0, 10, grid_size)
|
|
222
|
+
y = np.linspace(0, 10, grid_size)
|
|
223
|
+
X, Y = np.meshgrid(x, y)
|
|
224
|
+
Z = np.sin(X) * np.cos(Y) + 0.1 * np.random.randn(grid_size, grid_size)
|
|
225
|
+
|
|
226
|
+
start_time = time.time()
|
|
227
|
+
|
|
228
|
+
fig, ax = plt.subplots()
|
|
229
|
+
contour = ax.contourf(X, Y, Z, levels=levels, cmap="viridis")
|
|
230
|
+
plt.colorbar(contour, ax=ax)
|
|
231
|
+
ax.set_xlabel("X")
|
|
232
|
+
ax.set_ylabel("Y")
|
|
233
|
+
ax.set_title(f"Contour - {grid_size}x{grid_size} grid, {levels} levels")
|
|
234
|
+
|
|
235
|
+
end_time = time.time()
|
|
236
|
+
elapsed = end_time - start_time
|
|
237
|
+
|
|
238
|
+
plt.close(fig)
|
|
239
|
+
|
|
240
|
+
# Contour plots scale with grid size and levels
|
|
241
|
+
expected_time = (
|
|
242
|
+
(grid_size / 50) * (levels / 10) * 2.0
|
|
243
|
+
) # Base expectation
|
|
244
|
+
assert (
|
|
245
|
+
elapsed < expected_time
|
|
246
|
+
), f"Contour plot took {elapsed:.3f}s (expected < {expected_time:.3f}s)"
|
|
247
|
+
|
|
248
|
+
def test_subplot_performance(self):
|
|
249
|
+
"""Test performance of multi-subplot layouts."""
|
|
250
|
+
subplot_counts = [4, 9, 16, 25] # 2x2, 3x3, 4x4, 5x5
|
|
251
|
+
|
|
252
|
+
for n_subplots in subplot_counts:
|
|
253
|
+
grid_size = int(np.sqrt(n_subplots))
|
|
254
|
+
|
|
255
|
+
start_time = time.time()
|
|
256
|
+
|
|
257
|
+
fig, axes = plt.subplots(grid_size, grid_size, figsize=(12, 12))
|
|
258
|
+
axes_flat = axes.flatten() if hasattr(axes, "flatten") else [axes]
|
|
259
|
+
|
|
260
|
+
for i, ax in enumerate(axes_flat):
|
|
261
|
+
x = np.linspace(0, 10, 1000)
|
|
262
|
+
y = np.sin(x + i * np.pi / 4)
|
|
263
|
+
ax.plot(x, y)
|
|
264
|
+
ax.set_title(f"Subplot {i+1}")
|
|
265
|
+
ax.grid(True, alpha=0.3)
|
|
266
|
+
|
|
267
|
+
plt.tight_layout()
|
|
268
|
+
|
|
269
|
+
end_time = time.time()
|
|
270
|
+
elapsed = end_time - start_time
|
|
271
|
+
|
|
272
|
+
plt.close(fig)
|
|
273
|
+
|
|
274
|
+
# Subplot creation should scale linearly
|
|
275
|
+
expected_time = n_subplots * 0.1 # 0.1s per subplot
|
|
276
|
+
assert (
|
|
277
|
+
elapsed < expected_time + 2.0
|
|
278
|
+
), f"{n_subplots} subplots took {elapsed:.3f}s"
|
|
279
|
+
|
|
280
|
+
def test_repeated_plot_performance(self):
|
|
281
|
+
"""Test performance of repeated plot creation/destruction."""
|
|
282
|
+
n_iterations = 50
|
|
283
|
+
data_size = 10000
|
|
284
|
+
|
|
285
|
+
times = []
|
|
286
|
+
|
|
287
|
+
for i in range(n_iterations):
|
|
288
|
+
x = np.linspace(0, 10, data_size)
|
|
289
|
+
y = np.sin(x) + 0.1 * np.random.randn(data_size)
|
|
290
|
+
|
|
291
|
+
start_time = time.time()
|
|
292
|
+
|
|
293
|
+
fig, ax = plt.subplots()
|
|
294
|
+
ax.plot(x, y)
|
|
295
|
+
ax.set_xlabel("X")
|
|
296
|
+
ax.set_ylabel("Y")
|
|
297
|
+
ax.set_title(f"Iteration {i+1}")
|
|
298
|
+
|
|
299
|
+
plt.close(fig)
|
|
300
|
+
|
|
301
|
+
end_time = time.time()
|
|
302
|
+
elapsed = end_time - start_time
|
|
303
|
+
times.append(elapsed)
|
|
304
|
+
|
|
305
|
+
# Check for performance degradation over time
|
|
306
|
+
early_times = np.mean(times[:10])
|
|
307
|
+
late_times = np.mean(times[-10:])
|
|
308
|
+
|
|
309
|
+
# Late times shouldn't be significantly slower (indicating memory leaks)
|
|
310
|
+
degradation_ratio = late_times / early_times
|
|
311
|
+
assert (
|
|
312
|
+
degradation_ratio < 2.0
|
|
313
|
+
), f"Performance degraded by {degradation_ratio:.2f}x over {n_iterations} iterations"
|
|
314
|
+
|
|
315
|
+
# Average time per iteration should be reasonable
|
|
316
|
+
avg_time = np.mean(times)
|
|
317
|
+
assert (
|
|
318
|
+
avg_time < 1.0
|
|
319
|
+
), f"Average time per plot: {avg_time:.3f}s (expected < 1.0s)"
|
|
320
|
+
|
|
321
|
+
|
|
322
|
+
class TestDataTypePerformance:
|
|
323
|
+
"""Test performance with different data types and structures."""
|
|
324
|
+
|
|
325
|
+
def teardown_method(self):
|
|
326
|
+
"""Clean up after performance tests."""
|
|
327
|
+
plt.close("all")
|
|
328
|
+
gc.collect()
|
|
329
|
+
|
|
330
|
+
def test_pandas_integration_performance(self):
|
|
331
|
+
"""Test performance when plotting with pandas DataFrames."""
|
|
332
|
+
sizes = [1000, 10000, 50000]
|
|
333
|
+
|
|
334
|
+
for size in sizes:
|
|
335
|
+
# Create pandas DataFrame
|
|
336
|
+
dates = pd.date_range("2023-01-01", periods=size, freq="1min")
|
|
337
|
+
data = pd.DataFrame(
|
|
338
|
+
{
|
|
339
|
+
"param1": np.random.randn(size).cumsum(),
|
|
340
|
+
"param2": np.random.randn(size).cumsum(),
|
|
341
|
+
"param3": np.random.randn(size).cumsum(),
|
|
342
|
+
},
|
|
343
|
+
index=dates,
|
|
344
|
+
)
|
|
345
|
+
|
|
346
|
+
start_time = time.time()
|
|
347
|
+
|
|
348
|
+
fig, axes = plt.subplots(3, 1, figsize=(12, 10), sharex=True)
|
|
349
|
+
|
|
350
|
+
for i, column in enumerate(data.columns):
|
|
351
|
+
axes[i].plot(data.index, data[column], label=column)
|
|
352
|
+
axes[i].set_ylabel(column)
|
|
353
|
+
axes[i].legend()
|
|
354
|
+
axes[i].grid(True, alpha=0.3)
|
|
355
|
+
|
|
356
|
+
axes[-1].set_xlabel("Time")
|
|
357
|
+
plt.tight_layout()
|
|
358
|
+
|
|
359
|
+
end_time = time.time()
|
|
360
|
+
elapsed = end_time - start_time
|
|
361
|
+
|
|
362
|
+
plt.close(fig)
|
|
363
|
+
|
|
364
|
+
# Pandas plotting should be reasonably fast
|
|
365
|
+
expected_time = size / 10000 * 2.0 # Scale with data size
|
|
366
|
+
assert (
|
|
367
|
+
elapsed < expected_time
|
|
368
|
+
), f"Pandas plot with {size} points took {elapsed:.3f}s"
|
|
369
|
+
|
|
370
|
+
def test_different_data_types_performance(self):
|
|
371
|
+
"""Test performance with different numpy data types."""
|
|
372
|
+
size = 50000
|
|
373
|
+
data_types = [np.float32, np.float64, np.int32, np.int64]
|
|
374
|
+
|
|
375
|
+
x = np.linspace(0, 10, size)
|
|
376
|
+
|
|
377
|
+
for dtype in data_types:
|
|
378
|
+
y = (np.sin(x) * 1000).astype(dtype)
|
|
379
|
+
|
|
380
|
+
start_time = time.time()
|
|
381
|
+
|
|
382
|
+
fig, ax = plt.subplots()
|
|
383
|
+
ax.plot(x, y)
|
|
384
|
+
ax.set_xlabel("X")
|
|
385
|
+
ax.set_ylabel(f"Y ({dtype.__name__})")
|
|
386
|
+
ax.set_title(f"Performance Test - {dtype.__name__}")
|
|
387
|
+
|
|
388
|
+
end_time = time.time()
|
|
389
|
+
elapsed = end_time - start_time
|
|
390
|
+
|
|
391
|
+
plt.close(fig)
|
|
392
|
+
|
|
393
|
+
# All data types should have similar performance
|
|
394
|
+
assert elapsed < 5.0, f"Plot with {dtype.__name__} took {elapsed:.3f}s"
|
|
395
|
+
|
|
396
|
+
def test_sparse_data_performance(self):
|
|
397
|
+
"""Test performance with sparse/irregular data."""
|
|
398
|
+
# Test with data that has irregular spacing
|
|
399
|
+
n_points = 10000
|
|
400
|
+
|
|
401
|
+
# Regular spacing
|
|
402
|
+
x_regular = np.linspace(0, 100, n_points)
|
|
403
|
+
y_regular = np.sin(x_regular)
|
|
404
|
+
|
|
405
|
+
start_time = time.time()
|
|
406
|
+
fig, ax = plt.subplots()
|
|
407
|
+
ax.plot(x_regular, y_regular)
|
|
408
|
+
ax.set_title("Regular Spacing")
|
|
409
|
+
end_time = time.time()
|
|
410
|
+
regular_time = end_time - start_time
|
|
411
|
+
plt.close(fig)
|
|
412
|
+
|
|
413
|
+
# Irregular spacing (clustered points)
|
|
414
|
+
x_irregular = np.sort(np.random.exponential(0.1, n_points))
|
|
415
|
+
y_irregular = np.sin(x_irregular)
|
|
416
|
+
|
|
417
|
+
start_time = time.time()
|
|
418
|
+
fig, ax = plt.subplots()
|
|
419
|
+
ax.plot(x_irregular, y_irregular)
|
|
420
|
+
ax.set_title("Irregular Spacing")
|
|
421
|
+
end_time = time.time()
|
|
422
|
+
irregular_time = end_time - start_time
|
|
423
|
+
plt.close(fig)
|
|
424
|
+
|
|
425
|
+
# Irregular data shouldn't be significantly slower
|
|
426
|
+
time_ratio = irregular_time / regular_time
|
|
427
|
+
assert time_ratio < 2.0, f"Irregular data {time_ratio:.2f}x slower than regular"
|
|
428
|
+
|
|
429
|
+
|
|
430
|
+
class TestMemoryEfficiency:
|
|
431
|
+
"""Test memory efficiency of plotting operations."""
|
|
432
|
+
|
|
433
|
+
def setup_method(self):
|
|
434
|
+
"""Set up memory efficiency tests."""
|
|
435
|
+
gc.collect()
|
|
436
|
+
self.process = psutil.Process(os.getpid())
|
|
437
|
+
|
|
438
|
+
def teardown_method(self):
|
|
439
|
+
"""Clean up after memory tests."""
|
|
440
|
+
plt.close("all")
|
|
441
|
+
gc.collect()
|
|
442
|
+
|
|
443
|
+
def get_memory_usage(self):
|
|
444
|
+
"""Get current memory usage in MB."""
|
|
445
|
+
return self.process.memory_info().rss / 1024 / 1024
|
|
446
|
+
|
|
447
|
+
def test_memory_cleanup(self):
|
|
448
|
+
"""Test that memory is properly released after plots are closed."""
|
|
449
|
+
initial_memory = self.get_memory_usage()
|
|
450
|
+
|
|
451
|
+
# Create and close many plots
|
|
452
|
+
for i in range(20):
|
|
453
|
+
x = np.linspace(0, 10, 10000)
|
|
454
|
+
y = np.sin(x) + 0.1 * np.random.randn(10000)
|
|
455
|
+
|
|
456
|
+
fig, ax = plt.subplots(figsize=(12, 8))
|
|
457
|
+
ax.plot(x, y)
|
|
458
|
+
ax.set_xlabel("X")
|
|
459
|
+
ax.set_ylabel("Y")
|
|
460
|
+
ax.set_title(f"Memory Test {i+1}")
|
|
461
|
+
ax.grid(True)
|
|
462
|
+
|
|
463
|
+
plt.close(fig)
|
|
464
|
+
|
|
465
|
+
# Force garbage collection every few iterations
|
|
466
|
+
if i % 5 == 0:
|
|
467
|
+
gc.collect()
|
|
468
|
+
|
|
469
|
+
# Final cleanup
|
|
470
|
+
gc.collect()
|
|
471
|
+
final_memory = self.get_memory_usage()
|
|
472
|
+
|
|
473
|
+
# Memory increase should be minimal
|
|
474
|
+
memory_increase = final_memory - initial_memory
|
|
475
|
+
assert (
|
|
476
|
+
memory_increase < 50
|
|
477
|
+
), f"Memory increased by {memory_increase:.1f}MB after 20 plots"
|
|
478
|
+
|
|
479
|
+
def test_large_figure_memory(self):
|
|
480
|
+
"""Test memory usage with large figure sizes."""
|
|
481
|
+
sizes = [(8, 6), (16, 12), (24, 18), (32, 24)]
|
|
482
|
+
memory_usages = []
|
|
483
|
+
|
|
484
|
+
for width, height in sizes:
|
|
485
|
+
gc.collect()
|
|
486
|
+
mem_before = self.get_memory_usage()
|
|
487
|
+
|
|
488
|
+
fig, ax = plt.subplots(figsize=(width, height), dpi=100)
|
|
489
|
+
x = np.linspace(0, 10, 50000)
|
|
490
|
+
y = np.sin(x)
|
|
491
|
+
ax.plot(x, y)
|
|
492
|
+
ax.set_xlabel("X")
|
|
493
|
+
ax.set_ylabel("Y")
|
|
494
|
+
ax.set_title(f"Large Figure {width}x{height}")
|
|
495
|
+
|
|
496
|
+
mem_after = self.get_memory_usage()
|
|
497
|
+
memory_increase = mem_after - mem_before
|
|
498
|
+
memory_usages.append(memory_increase)
|
|
499
|
+
|
|
500
|
+
plt.close(fig)
|
|
501
|
+
|
|
502
|
+
# Memory should scale reasonably with figure size
|
|
503
|
+
area = width * height
|
|
504
|
+
memory_per_area = memory_increase / area
|
|
505
|
+
assert (
|
|
506
|
+
memory_per_area < 2.0
|
|
507
|
+
), f"Memory per area: {memory_per_area:.3f} MB per unit²"
|
|
508
|
+
|
|
509
|
+
print(f"Figure size memory usage: {list(zip(sizes, memory_usages))}")
|
|
510
|
+
|
|
511
|
+
|
|
512
|
+
@pytest.mark.slow
|
|
513
|
+
class TestLargeDatasetPerformance:
|
|
514
|
+
"""Test performance with datasets typical of space physics applications."""
|
|
515
|
+
|
|
516
|
+
def teardown_method(self):
|
|
517
|
+
"""Clean up after large dataset tests."""
|
|
518
|
+
plt.close("all")
|
|
519
|
+
gc.collect()
|
|
520
|
+
|
|
521
|
+
def test_space_physics_timeseries_performance(self):
|
|
522
|
+
"""Test performance with typical space physics time series."""
|
|
523
|
+
# Simulate 1 year of 1-minute cadence data
|
|
524
|
+
n_points = 365 * 24 * 60 # ~525,600 points
|
|
525
|
+
|
|
526
|
+
print(f"Testing with {n_points:,} data points (1 year of 1-min data)")
|
|
527
|
+
|
|
528
|
+
# Create realistic space physics data
|
|
529
|
+
times = pd.date_range("2023-01-01", periods=n_points, freq="1min")
|
|
530
|
+
|
|
531
|
+
# Solar wind parameters with realistic variations
|
|
532
|
+
np.random.seed(42)
|
|
533
|
+
density = 10 * (
|
|
534
|
+
1
|
|
535
|
+
+ 0.5 * np.sin(np.arange(n_points) / (24 * 60)) # Daily variation
|
|
536
|
+
+ 0.2 * np.sin(np.arange(n_points) / (27 * 24 * 60)) # Solar rotation
|
|
537
|
+
+ 0.1 * np.random.randn(n_points)
|
|
538
|
+
) # Random noise
|
|
539
|
+
|
|
540
|
+
velocity = 400 * (
|
|
541
|
+
1
|
|
542
|
+
+ 0.3 * np.sin(np.arange(n_points) / (27 * 24 * 60))
|
|
543
|
+
+ 0.1 * np.random.randn(n_points)
|
|
544
|
+
)
|
|
545
|
+
|
|
546
|
+
temperature = 1e5 * (
|
|
547
|
+
1
|
|
548
|
+
+ 0.4 * np.sin(np.arange(n_points) / (24 * 60))
|
|
549
|
+
+ 0.2 * np.random.randn(n_points)
|
|
550
|
+
)
|
|
551
|
+
|
|
552
|
+
data = pd.DataFrame(
|
|
553
|
+
{"density": density, "velocity": velocity, "temperature": temperature},
|
|
554
|
+
index=times,
|
|
555
|
+
)
|
|
556
|
+
|
|
557
|
+
start_time = time.time()
|
|
558
|
+
|
|
559
|
+
# Create multi-panel time series plot
|
|
560
|
+
fig, axes = plt.subplots(3, 1, figsize=(15, 12), sharex=True)
|
|
561
|
+
|
|
562
|
+
parameters = ["density", "velocity", "temperature"]
|
|
563
|
+
labels = ["Density (cm⁻³)", "Velocity (km/s)", "Temperature (K)"]
|
|
564
|
+
colors = ["blue", "red", "green"]
|
|
565
|
+
|
|
566
|
+
for ax, param, label, color in zip(axes, parameters, labels, colors):
|
|
567
|
+
ax.plot(data.index, data[param], color=color, linewidth=0.5, alpha=0.8)
|
|
568
|
+
ax.set_ylabel(label)
|
|
569
|
+
ax.grid(True, alpha=0.3)
|
|
570
|
+
|
|
571
|
+
# Add rolling mean for trend
|
|
572
|
+
rolling_mean = data[param].rolling(window=60 * 24).mean() # Daily average
|
|
573
|
+
ax.plot(data.index, rolling_mean, color="black", linewidth=2, alpha=0.7)
|
|
574
|
+
|
|
575
|
+
axes[-1].set_xlabel("Time")
|
|
576
|
+
plt.suptitle("Space Physics Time Series - 1 Year of Data", fontsize=14)
|
|
577
|
+
plt.tight_layout()
|
|
578
|
+
|
|
579
|
+
end_time = time.time()
|
|
580
|
+
elapsed = end_time - start_time
|
|
581
|
+
|
|
582
|
+
plt.close(fig)
|
|
583
|
+
|
|
584
|
+
# Should handle large datasets in reasonable time
|
|
585
|
+
assert (
|
|
586
|
+
elapsed < 30.0
|
|
587
|
+
), f"Large dataset plot took {elapsed:.3f}s (expected < 30s)"
|
|
588
|
+
print(f"Large dataset plot completed in {elapsed:.3f}s")
|
|
589
|
+
|
|
590
|
+
def test_high_resolution_contour_performance(self):
|
|
591
|
+
"""Test performance with high-resolution 2D data."""
|
|
592
|
+
# High-resolution grid typical of simulation data
|
|
593
|
+
nx, ny = 500, 500
|
|
594
|
+
print(f"Testing contour plot with {nx}x{ny} = {nx*ny:,} grid points")
|
|
595
|
+
|
|
596
|
+
x = np.linspace(0, 10, nx)
|
|
597
|
+
y = np.linspace(0, 10, ny)
|
|
598
|
+
X, Y = np.meshgrid(x, y)
|
|
599
|
+
|
|
600
|
+
# Complex 2D function with multiple scales
|
|
601
|
+
Z = (
|
|
602
|
+
np.sin(X) * np.cos(Y)
|
|
603
|
+
+ 0.5 * np.sin(5 * X) * np.cos(5 * Y)
|
|
604
|
+
+ 0.1 * np.sin(20 * X) * np.cos(20 * Y)
|
|
605
|
+
+ 0.05 * np.random.randn(nx, ny)
|
|
606
|
+
)
|
|
607
|
+
|
|
608
|
+
start_time = time.time()
|
|
609
|
+
|
|
610
|
+
fig, axes = plt.subplots(2, 2, figsize=(12, 12))
|
|
611
|
+
|
|
612
|
+
# Filled contour
|
|
613
|
+
contourf = axes[0, 0].contourf(X, Y, Z, levels=50, cmap="viridis")
|
|
614
|
+
axes[0, 0].set_title("Filled Contour")
|
|
615
|
+
plt.colorbar(contourf, ax=axes[0, 0])
|
|
616
|
+
|
|
617
|
+
# Line contour
|
|
618
|
+
contour = axes[0, 1].contour(X, Y, Z, levels=20, colors="black")
|
|
619
|
+
axes[0, 1].set_title("Line Contour")
|
|
620
|
+
axes[0, 1].clabel(contour, inline=True, fontsize=8)
|
|
621
|
+
|
|
622
|
+
# Image plot
|
|
623
|
+
im = axes[1, 0].imshow(Z, extent=[0, 10, 0, 10], cmap="plasma", aspect="auto")
|
|
624
|
+
axes[1, 0].set_title("Image Plot")
|
|
625
|
+
plt.colorbar(im, ax=axes[1, 0])
|
|
626
|
+
|
|
627
|
+
# Pcolormesh
|
|
628
|
+
pcm = axes[1, 1].pcolormesh(X, Y, Z, cmap="coolwarm")
|
|
629
|
+
axes[1, 1].set_title("Pcolormesh")
|
|
630
|
+
plt.colorbar(pcm, ax=axes[1, 1])
|
|
631
|
+
|
|
632
|
+
plt.tight_layout()
|
|
633
|
+
|
|
634
|
+
end_time = time.time()
|
|
635
|
+
elapsed = end_time - start_time
|
|
636
|
+
|
|
637
|
+
plt.close(fig)
|
|
638
|
+
|
|
639
|
+
# High-resolution 2D plots are computationally intensive
|
|
640
|
+
assert (
|
|
641
|
+
elapsed < 60.0
|
|
642
|
+
), f"High-res contour plot took {elapsed:.3f}s (expected < 60s)"
|
|
643
|
+
print(f"High-resolution contour plot completed in {elapsed:.3f}s")
|
|
644
|
+
|
|
645
|
+
|
|
646
|
+
def test_performance_regression():
|
|
647
|
+
"""Test for performance regressions in basic operations."""
|
|
648
|
+
# This test establishes baseline performance expectations
|
|
649
|
+
# Values should be updated if significant performance improvements are made
|
|
650
|
+
|
|
651
|
+
# Basic line plot performance
|
|
652
|
+
x = np.linspace(0, 10, 100000)
|
|
653
|
+
y = np.sin(x)
|
|
654
|
+
|
|
655
|
+
start_time = time.time()
|
|
656
|
+
fig, ax = plt.subplots()
|
|
657
|
+
ax.plot(x, y)
|
|
658
|
+
ax.set_xlabel("X")
|
|
659
|
+
ax.set_ylabel("Y")
|
|
660
|
+
ax.set_title("Performance Regression Test")
|
|
661
|
+
end_time = time.time()
|
|
662
|
+
|
|
663
|
+
elapsed = end_time - start_time
|
|
664
|
+
plt.close(fig)
|
|
665
|
+
|
|
666
|
+
# Baseline expectation: 100k points should plot in under 2 seconds
|
|
667
|
+
assert elapsed < 2.0, f"Basic plot regression: {elapsed:.3f}s > 2.0s"
|
|
668
|
+
|
|
669
|
+
|
|
670
|
+
def test_memory_leak_detection():
|
|
671
|
+
"""Test for memory leaks in plotting operations."""
|
|
672
|
+
gc.collect()
|
|
673
|
+
process = psutil.Process(os.getpid())
|
|
674
|
+
initial_memory = process.memory_info().rss / 1024 / 1024
|
|
675
|
+
|
|
676
|
+
# Create and destroy many plots
|
|
677
|
+
for i in range(100):
|
|
678
|
+
fig, ax = plt.subplots()
|
|
679
|
+
x = np.random.randn(1000)
|
|
680
|
+
y = np.random.randn(1000)
|
|
681
|
+
ax.scatter(x, y, alpha=0.6)
|
|
682
|
+
plt.close(fig)
|
|
683
|
+
|
|
684
|
+
# Periodic cleanup
|
|
685
|
+
if i % 20 == 0:
|
|
686
|
+
gc.collect()
|
|
687
|
+
|
|
688
|
+
gc.collect()
|
|
689
|
+
final_memory = process.memory_info().rss / 1024 / 1024
|
|
690
|
+
memory_increase = final_memory - initial_memory
|
|
691
|
+
|
|
692
|
+
# Memory increase should be minimal after 100 plot cycles
|
|
693
|
+
assert (
|
|
694
|
+
memory_increase < 20
|
|
695
|
+
), f"Potential memory leak: {memory_increase:.1f}MB increase"
|
|
696
|
+
|
|
697
|
+
|
|
698
|
+
if __name__ == "__main__":
|
|
699
|
+
# Run basic performance tests when script is executed directly
|
|
700
|
+
print("Running basic performance tests...")
|
|
701
|
+
|
|
702
|
+
test = TestBasicPerformance()
|
|
703
|
+
test.setup_method()
|
|
704
|
+
test.test_line_plot_performance()
|
|
705
|
+
test.test_scatter_plot_performance()
|
|
706
|
+
test.teardown_method()
|
|
707
|
+
|
|
708
|
+
print("Performance tests completed successfully!")
|