ed-master-smartsolver 0.1.0__tar.gz
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.
- ed_master_smartsolver-0.1.0/.gitignore +25 -0
- ed_master_smartsolver-0.1.0/LICENSE +21 -0
- ed_master_smartsolver-0.1.0/PKG-INFO +355 -0
- ed_master_smartsolver-0.1.0/README.md +325 -0
- ed_master_smartsolver-0.1.0/__init__.py +34 -0
- ed_master_smartsolver-0.1.0/math_step_tracker.py +946 -0
- ed_master_smartsolver-0.1.0/pyproject.toml +68 -0
- ed_master_smartsolver-0.1.0/tests/test_smartsolver.py +48 -0
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# Build / publish
|
|
2
|
+
dist/
|
|
3
|
+
build/
|
|
4
|
+
*.egg-info/
|
|
5
|
+
.eggs/
|
|
6
|
+
|
|
7
|
+
# Virtual environments
|
|
8
|
+
.venv/
|
|
9
|
+
venv/
|
|
10
|
+
env/
|
|
11
|
+
|
|
12
|
+
# Python
|
|
13
|
+
__pycache__/
|
|
14
|
+
*.py[cod]
|
|
15
|
+
.pytest_cache/
|
|
16
|
+
.mypy_cache/
|
|
17
|
+
.ruff_cache/
|
|
18
|
+
|
|
19
|
+
# IDE
|
|
20
|
+
.idea/
|
|
21
|
+
.vscode/
|
|
22
|
+
*.swp
|
|
23
|
+
|
|
24
|
+
# Twine / secrets
|
|
25
|
+
.pypirc
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Ed-Master
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
|
@@ -0,0 +1,355 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: ed-master-smartsolver
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Step-by-step mathematics solver built on SymPy — equations, calculus, and annotated rules.
|
|
5
|
+
Project-URL: Homepage, https://www.ed-master.co.za
|
|
6
|
+
Project-URL: Repository, https://github.com/mngadilinda/SmartSolver
|
|
7
|
+
Project-URL: Documentation, https://github.com/mngadilinda/SmartSolver#readme
|
|
8
|
+
Author-email: Ed-Master <support@ed-master.co.za>
|
|
9
|
+
License-Expression: MIT
|
|
10
|
+
License-File: LICENSE
|
|
11
|
+
Keywords: algebra,calculus,education,math,solver,step-by-step,sympy
|
|
12
|
+
Classifier: Development Status :: 4 - Beta
|
|
13
|
+
Classifier: Intended Audience :: Developers
|
|
14
|
+
Classifier: Intended Audience :: Education
|
|
15
|
+
Classifier: License :: OSI Approved :: MIT License
|
|
16
|
+
Classifier: Programming Language :: Python :: 3
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
20
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
21
|
+
Classifier: Topic :: Education
|
|
22
|
+
Classifier: Topic :: Scientific/Engineering :: Mathematics
|
|
23
|
+
Requires-Python: >=3.10
|
|
24
|
+
Requires-Dist: sympy>=1.13
|
|
25
|
+
Provides-Extra: dev
|
|
26
|
+
Requires-Dist: build; extra == 'dev'
|
|
27
|
+
Requires-Dist: pytest; extra == 'dev'
|
|
28
|
+
Requires-Dist: twine; extra == 'dev'
|
|
29
|
+
Description-Content-Type: text/markdown
|
|
30
|
+
|
|
31
|
+
# SmartSolver
|
|
32
|
+
|
|
33
|
+
**SmartSolver** is a step-by-step mathematics engine built on [SymPy](https://www.sympy.org/). It powers worked solutions inside [Ed-Master](https://www.ed-master.co.za) — showing not just the final answer, but the rules and identities applied along the way.
|
|
34
|
+
|
|
35
|
+
The implementation lives in `math_step_tracker.py` (class `SmartSolver`).
|
|
36
|
+
|
|
37
|
+
---
|
|
38
|
+
|
|
39
|
+
## Features
|
|
40
|
+
|
|
41
|
+
| Area | What SmartSolver shows |
|
|
42
|
+
|------|------------------------|
|
|
43
|
+
| **Equations** | Linear & quadratic solving, discriminant steps |
|
|
44
|
+
| **Trigonometry** | Quotient, Pythagorean, double-angle identities; tan reduction |
|
|
45
|
+
| **Logarithms & exponentials** | Log product/power rules, `log(x) = c → x = e^c`, `a^x = b` |
|
|
46
|
+
| **Differentiation** | Sum, product, power, chain rule labels |
|
|
47
|
+
| **Integration** | Partial fractions, LIATE-based integration by parts, direct rules |
|
|
48
|
+
| **Limits** | Setup, direct substitution where valid, final limit |
|
|
49
|
+
| **Partial fractions** | Factor denominator, decompose, integrate term-by-term |
|
|
50
|
+
|
|
51
|
+
Each step includes a **description**, **expression**, **LaTeX**, and **rule applied**.
|
|
52
|
+
|
|
53
|
+
---
|
|
54
|
+
|
|
55
|
+
## Requirements
|
|
56
|
+
|
|
57
|
+
- **Python 3.10+** (`requires-python` in `pyproject.toml`)
|
|
58
|
+
- **SymPy ≥ 1.13**
|
|
59
|
+
|
|
60
|
+
### Supported Python versions
|
|
61
|
+
|
|
62
|
+
| Status | Versions |
|
|
63
|
+
|--------|----------|
|
|
64
|
+
| Minimum | Python **3.10** |
|
|
65
|
+
| Tested | Python **3.10**, **3.11**, **3.12**, **3.13** |
|
|
66
|
+
|
|
67
|
+
Only list versions you actually test. Do **not** claim support for unreleased major versions (e.g. Python 4.x or fictional 7.x).
|
|
68
|
+
|
|
69
|
+
```bash
|
|
70
|
+
pip install ed-master-smartsolver
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
Import in Python (package module name is `smartsolver`):
|
|
74
|
+
|
|
75
|
+
```python
|
|
76
|
+
from smartsolver import SmartSolver
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
Or install SymPy only when using from source:
|
|
80
|
+
|
|
81
|
+
```bash
|
|
82
|
+
pip install sympy
|
|
83
|
+
```
|
|
84
|
+
|
|
85
|
+
---
|
|
86
|
+
|
|
87
|
+
## Quick start
|
|
88
|
+
|
|
89
|
+
```python
|
|
90
|
+
from smartsolver import SmartSolver, StepRenderer, serialize_solver_result
|
|
91
|
+
|
|
92
|
+
solver = SmartSolver()
|
|
93
|
+
|
|
94
|
+
# Solve a quadratic
|
|
95
|
+
result = solver.solve_equation("x^2 + 5x + 6 = 0", "x")
|
|
96
|
+
print(StepRenderer.to_text(result["steps"]))
|
|
97
|
+
print("Solutions:", result["solutions"])
|
|
98
|
+
|
|
99
|
+
# JSON-friendly payload (for APIs)
|
|
100
|
+
payload = serialize_solver_result(result)
|
|
101
|
+
print(payload["steps_latex"])
|
|
102
|
+
```
|
|
103
|
+
|
|
104
|
+
When running from a git checkout (editable install):
|
|
105
|
+
|
|
106
|
+
```bash
|
|
107
|
+
pip install -e .
|
|
108
|
+
```
|
|
109
|
+
|
|
110
|
+
```python
|
|
111
|
+
from smartsolver import SmartSolver
|
|
112
|
+
```
|
|
113
|
+
|
|
114
|
+
---
|
|
115
|
+
|
|
116
|
+
## Input notation
|
|
117
|
+
|
|
118
|
+
SmartSolver accepts student-style strings:
|
|
119
|
+
|
|
120
|
+
| You type | Parsed as |
|
|
121
|
+
|----------|-----------|
|
|
122
|
+
| `x^2` or `x**2` | x squared |
|
|
123
|
+
| `5x` | `5*x` |
|
|
124
|
+
| `2x - 4` | `2x - 4 = 0` (equation assumed zero) |
|
|
125
|
+
| `sin(x)`, `cos(x)`, `log(x)` | SymPy trig / natural log |
|
|
126
|
+
| `2**x` | exponential |
|
|
127
|
+
|
|
128
|
+
---
|
|
129
|
+
|
|
130
|
+
## Operations
|
|
131
|
+
|
|
132
|
+
### `solve_equation(equation, variable='x')`
|
|
133
|
+
|
|
134
|
+
Solve an equation with step-by-step working.
|
|
135
|
+
|
|
136
|
+
```python
|
|
137
|
+
solver.solve_equation("sin(x) - cos(x) = 0", "x")
|
|
138
|
+
solver.solve_equation("2**x - 8 = 0", "x")
|
|
139
|
+
solver.solve_equation("log(x) - 3 = 0", "x")
|
|
140
|
+
```
|
|
141
|
+
|
|
142
|
+
**Returns:** `steps`, `solutions`, `solution_latex`
|
|
143
|
+
|
|
144
|
+
---
|
|
145
|
+
|
|
146
|
+
### `differentiate(expression, variable='x', order=1)`
|
|
147
|
+
|
|
148
|
+
Differentiate with rule labels (sum, power, chain, etc.).
|
|
149
|
+
|
|
150
|
+
```python
|
|
151
|
+
solver.differentiate("x**2 + 3*x", "x")
|
|
152
|
+
solver.differentiate("sin(x)**2", "x", order=1)
|
|
153
|
+
```
|
|
154
|
+
|
|
155
|
+
**Returns:** `steps`, `derivative`, `derivative_latex`
|
|
156
|
+
|
|
157
|
+
---
|
|
158
|
+
|
|
159
|
+
### `integrate(expression, variable='x', lower=None, upper=None)`
|
|
160
|
+
|
|
161
|
+
Integrate with method tracking.
|
|
162
|
+
|
|
163
|
+
```python
|
|
164
|
+
solver.integrate("x*exp(x)", "x") # integration by parts (LIATE)
|
|
165
|
+
solver.integrate("1/(x**2 - 1)", "x") # partial fractions
|
|
166
|
+
solver.integrate("x**2", "x", lower="0", upper="1") # definite
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
**Returns:** `steps`, `integral`, `integral_latex`, `methods` (e.g. `['Integration by parts']`)
|
|
170
|
+
|
|
171
|
+
---
|
|
172
|
+
|
|
173
|
+
### `partial_fractions(expression, variable='x')`
|
|
174
|
+
|
|
175
|
+
Decompose a rational expression without integrating.
|
|
176
|
+
|
|
177
|
+
```python
|
|
178
|
+
solver.partial_fractions("(2*x + 3)/((x - 1)*(x + 2))")
|
|
179
|
+
```
|
|
180
|
+
|
|
181
|
+
**Returns:** `steps`, `decomposition`, `decomposition_latex`
|
|
182
|
+
|
|
183
|
+
---
|
|
184
|
+
|
|
185
|
+
### `limit(expression, variable='x', point='0', direction='+')`
|
|
186
|
+
|
|
187
|
+
Evaluate a limit with setup steps.
|
|
188
|
+
|
|
189
|
+
```python
|
|
190
|
+
solver.limit("sin(x)/x", "x", point="0", direction="+")
|
|
191
|
+
```
|
|
192
|
+
|
|
193
|
+
**Returns:** `steps`, `limit`, `limit_latex`
|
|
194
|
+
|
|
195
|
+
---
|
|
196
|
+
|
|
197
|
+
## Helper utilities
|
|
198
|
+
|
|
199
|
+
```python
|
|
200
|
+
from smartsolver import (
|
|
201
|
+
StepRenderer,
|
|
202
|
+
serialize_solver_result,
|
|
203
|
+
normalize_math_input,
|
|
204
|
+
parse_math,
|
|
205
|
+
step_to_dict,
|
|
206
|
+
)
|
|
207
|
+
|
|
208
|
+
# Human-readable steps
|
|
209
|
+
StepRenderer.to_text(steps)
|
|
210
|
+
StepRenderer.to_latex(steps)
|
|
211
|
+
StepRenderer.to_html(steps)
|
|
212
|
+
|
|
213
|
+
# API / JSON serialization
|
|
214
|
+
serialize_solver_result(result)
|
|
215
|
+
```
|
|
216
|
+
|
|
217
|
+
### Optional helpers (Ed-Master Math Lab)
|
|
218
|
+
|
|
219
|
+
If you also ship `edmathlab.py` alongside this package, it provides stdout-friendly wrappers. They are not included in the PyPI wheel by default.
|
|
220
|
+
|
|
221
|
+
---
|
|
222
|
+
|
|
223
|
+
## REST API (Ed-Master platform)
|
|
224
|
+
|
|
225
|
+
When the Django backend is running, authenticated users can call:
|
|
226
|
+
|
|
227
|
+
```
|
|
228
|
+
POST /api/math/steps/
|
|
229
|
+
Content-Type: application/json
|
|
230
|
+
```
|
|
231
|
+
|
|
232
|
+
**Body:**
|
|
233
|
+
|
|
234
|
+
```json
|
|
235
|
+
{
|
|
236
|
+
"operation": "solve",
|
|
237
|
+
"expression": "x^2 + 5x + 6 = 0",
|
|
238
|
+
"variable": "x"
|
|
239
|
+
}
|
|
240
|
+
```
|
|
241
|
+
|
|
242
|
+
**Operations:** `solve`, `differentiate`, `integrate`, `limit`, `partial_fractions`
|
|
243
|
+
|
|
244
|
+
**Response fields:** `steps`, `steps_text`, `steps_html`, `steps_latex`, `result`, `result_latex`, `operation`
|
|
245
|
+
|
|
246
|
+
Requires a signed-in Ed-Master session (JWT cookie).
|
|
247
|
+
|
|
248
|
+
---
|
|
249
|
+
|
|
250
|
+
## Result structure
|
|
251
|
+
|
|
252
|
+
Each step is a `Step` dataclass:
|
|
253
|
+
|
|
254
|
+
```python
|
|
255
|
+
@dataclass
|
|
256
|
+
class Step:
|
|
257
|
+
description: str # e.g. "Apply the quotient identity"
|
|
258
|
+
expression: str # SymPy string at this step
|
|
259
|
+
latex: str # LaTeX rendering
|
|
260
|
+
rule_applied: str # e.g. "Quotient identity", "LIATE: choose u"
|
|
261
|
+
substeps: list # nested steps (reserved)
|
|
262
|
+
```
|
|
263
|
+
|
|
264
|
+
`serialize_solver_result()` flattens this for JSON APIs and adds rendered `steps_text`, `steps_html`, and `steps_latex`.
|
|
265
|
+
|
|
266
|
+
---
|
|
267
|
+
|
|
268
|
+
## Example session
|
|
269
|
+
|
|
270
|
+
```python
|
|
271
|
+
from smartsolver import SmartSolver, StepRenderer
|
|
272
|
+
|
|
273
|
+
s = SmartSolver()
|
|
274
|
+
|
|
275
|
+
print("=== Quadratic ===")
|
|
276
|
+
r = s.solve_equation("x^2 + 5x + 6 = 0")
|
|
277
|
+
print(StepRenderer.to_text(r["steps"]))
|
|
278
|
+
|
|
279
|
+
print("=== Trig ===")
|
|
280
|
+
r = s.solve_equation("sin(x) - cos(x) = 0")
|
|
281
|
+
print(StepRenderer.to_text(r["steps"]))
|
|
282
|
+
|
|
283
|
+
print("=== Integration by parts ===")
|
|
284
|
+
r = s.integrate("x*exp(x)")
|
|
285
|
+
print(StepRenderer.to_text(r["steps"]))
|
|
286
|
+
print("Answer:", r["integral"])
|
|
287
|
+
print("Methods:", r["methods"])
|
|
288
|
+
```
|
|
289
|
+
|
|
290
|
+
---
|
|
291
|
+
|
|
292
|
+
## Scope & limitations
|
|
293
|
+
|
|
294
|
+
SmartSolver is designed for **education**, not as a replacement for a full computer algebra system.
|
|
295
|
+
|
|
296
|
+
- Trig: covers common identities and reduction; general periodic solution sets are simplified.
|
|
297
|
+
- Logs: strongest on combinable logs and `log(f(x)) = constant` forms.
|
|
298
|
+
- Partial fractions: requires a proper rational form; improper rationals use polynomial division first.
|
|
299
|
+
- Integration by parts: one LIATE-guided pass; does not recurse automatically.
|
|
300
|
+
- u-substitution: basic patterns only.
|
|
301
|
+
|
|
302
|
+
SymPy still performs the underlying symbolic work; SmartSolver adds **annotated steps** around it.
|
|
303
|
+
|
|
304
|
+
---
|
|
305
|
+
|
|
306
|
+
## Running tests
|
|
307
|
+
|
|
308
|
+
```bash
|
|
309
|
+
pip install -e ".[dev]"
|
|
310
|
+
python -m unittest discover -s tests -v
|
|
311
|
+
```
|
|
312
|
+
|
|
313
|
+
Or a quick smoke test:
|
|
314
|
+
|
|
315
|
+
```bash
|
|
316
|
+
python -c "from smartsolver import SmartSolver; print(SmartSolver().solve_equation('x-2=0')['solutions'])"
|
|
317
|
+
```
|
|
318
|
+
|
|
319
|
+
---
|
|
320
|
+
|
|
321
|
+
## Project layout
|
|
322
|
+
|
|
323
|
+
```
|
|
324
|
+
. # repository root (this folder)
|
|
325
|
+
├── __init__.py # public exports
|
|
326
|
+
├── math_step_tracker.py # SmartSolver core
|
|
327
|
+
├── README.md
|
|
328
|
+
├── LICENSE
|
|
329
|
+
├── pyproject.toml # PEP 517 build (no setup.py)
|
|
330
|
+
└── tests/
|
|
331
|
+
└── test_smartsolver.py
|
|
332
|
+
```
|
|
333
|
+
|
|
334
|
+
---
|
|
335
|
+
|
|
336
|
+
## Roadmap
|
|
337
|
+
|
|
338
|
+
- [x] PyPI packaging scaffold (`ed-master-smartsolver`)
|
|
339
|
+
- [ ] Recursive integration by parts
|
|
340
|
+
- [ ] Richer trig general solutions
|
|
341
|
+
- [ ] Public “Try SmartSolver” demo page on Ed-Master
|
|
342
|
+
|
|
343
|
+
---
|
|
344
|
+
|
|
345
|
+
## Links
|
|
346
|
+
|
|
347
|
+
- **Platform:** [ed-master.co.za](https://www.ed-master.co.za)
|
|
348
|
+
- **Try Math Lab:** [ed-master.co.za/try/math-lab](https://www.ed-master.co.za/try/math-lab)
|
|
349
|
+
- **Research projects:** [ed-master.co.za/projects](https://www.ed-master.co.za/projects)
|
|
350
|
+
|
|
351
|
+
---
|
|
352
|
+
|
|
353
|
+
## License
|
|
354
|
+
|
|
355
|
+
MIT — see [LICENSE](LICENSE).
|