starbash 0.1.35__tar.gz → 0.2.3__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.
Files changed (66) hide show
  1. {starbash-0.1.35 → starbash-0.2.3}/PKG-INFO +38 -30
  2. {starbash-0.1.35 → starbash-0.2.3}/README.md +36 -29
  3. {starbash-0.1.35 → starbash-0.2.3}/pyproject.toml +27 -3
  4. {starbash-0.1.35 → starbash-0.2.3}/src/repo/repo.py +6 -1
  5. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/__init__.py +1 -1
  6. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/analytics.py +3 -3
  7. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/app.py +49 -7
  8. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/commands/process.py +13 -7
  9. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/commands/user.py +3 -4
  10. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/doit.py +1 -2
  11. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/exception.py +11 -4
  12. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/paths.py +7 -2
  13. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/processed_target.py +4 -102
  14. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/processing.py +40 -91
  15. starbash-0.2.3/src/starbash/sim_siril/__init__.py +6 -0
  16. starbash-0.2.3/src/starbash/sim_siril/connection.py +79 -0
  17. starbash-0.2.3/src/starbash/sim_siril/enums.py +316 -0
  18. starbash-0.2.3/src/starbash/sim_siril/utility.py +32 -0
  19. starbash-0.2.3/src/starbash/stage_utils.py +45 -0
  20. starbash-0.2.3/src/starbash/stages.py +260 -0
  21. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/tool/context.py +74 -3
  22. starbash-0.2.3/src/starbash/tool/python.py +204 -0
  23. starbash-0.2.3/src/starbash/ui/main.py +92 -0
  24. starbash-0.1.35/src/starbash/tool/python.py +0 -84
  25. {starbash-0.1.35 → starbash-0.2.3}/LICENSE +0 -0
  26. {starbash-0.1.35 → starbash-0.2.3}/src/repo/__init__.py +0 -0
  27. {starbash-0.1.35 → starbash-0.2.3}/src/repo/http_client.py +0 -0
  28. {starbash-0.1.35 → starbash-0.2.3}/src/repo/manager.py +0 -0
  29. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/aliases.py +0 -0
  30. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/check_version.py +0 -0
  31. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/commands/__init__.py +0 -0
  32. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/commands/info.py +0 -0
  33. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/commands/repo.py +0 -0
  34. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/commands/select.py +0 -0
  35. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/database.py +0 -0
  36. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/defaults/__init__.py +0 -0
  37. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/defaults/starbash.toml +0 -0
  38. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/doit_types.py +0 -0
  39. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/dwarf3.py +0 -0
  40. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/filtering.py +0 -0
  41. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/icon.py +0 -0
  42. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/linux.py +0 -0
  43. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/main.py +0 -0
  44. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/os.py +0 -0
  45. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/parameters.py +0 -0
  46. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/processing_like.py +0 -0
  47. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/recipes/README.md +0 -0
  48. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/recipes/__init__.py +0 -0
  49. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/recipes/osc.py +0 -0
  50. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/rich.py +0 -0
  51. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/safety.py +0 -0
  52. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/score.py +0 -0
  53. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/selection.py +0 -0
  54. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/templates/__init__.py +0 -0
  55. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/templates/repo/master.toml +0 -0
  56. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/templates/repo/processed.toml +0 -0
  57. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/templates/target/master.toml +0 -0
  58. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/templates/target/processed.toml +0 -0
  59. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/templates/userconfig.toml +0 -0
  60. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/toml.py +0 -0
  61. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/tool/__init__.py +0 -0
  62. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/tool/base.py +0 -0
  63. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/tool/graxpert.py +0 -0
  64. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/tool/siril.py +0 -0
  65. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/url.py +0 -0
  66. {starbash-0.1.35 → starbash-0.2.3}/src/starbash/windows.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: starbash
3
- Version: 0.1.35
3
+ Version: 0.2.3
4
4
  Summary: A tool for automating/standardizing/sharing astrophotography workflows.
5
5
  License-File: LICENSE
6
6
  Author: Kevin Hester
@@ -19,6 +19,7 @@ Requires-Dist: requests-cache (>=1.2.1,<2.0.0)
19
19
  Requires-Dist: restrictedpython (>=8.1,<9.0)
20
20
  Requires-Dist: rich (>=14.2.0,<15.0.0)
21
21
  Requires-Dist: sentry-sdk (>=2.42.1,<3.0.0)
22
+ Requires-Dist: textual (>=6.8.0,<7.0.0)
22
23
  Requires-Dist: tomlkit (>=0.13.3,<0.14.0)
23
24
  Requires-Dist: typer (>=0.20.0,<0.21.0)
24
25
  Requires-Dist: update-checker (>=0.18.0,<0.19.0)
@@ -29,16 +30,18 @@ Description-Content-Type: text/markdown
29
30
 
30
31
  # [Starbash](https://github.com/geeksville/starbash)
31
32
 
32
- <img src="https://raw.githubusercontent.com/geeksville/starbash/refs/heads/main/doc/img/icon.jpg" alt="Starbash: Astrophotography workflows simplified" width="30%" align="right" style="margin-bottom: 20px;">
33
-
34
33
  [![PyPI - Version](https://img.shields.io/pypi/v/starbash)](https://pypi.org/project/starbash/)
35
34
  [![Continuous Integration](https://github.com/geeksville/starbash/actions/workflows/ci.yml/badge.svg)](https://github.com/geeksville/starbash/actions/workflows/ci.yml)
36
35
  [![codecov](https://codecov.io/github/geeksville/starbash/graph/badge.svg?token=47RE10I7O1)](https://codecov.io/github/geeksville/starbash)
37
36
 
38
37
  A tool for automating/standardizing/sharing astrophotography workflows.
39
38
 
40
- * Automatic - with sensible defaults that you can change as needed.
41
- * Easy - provides a 'seestar-like' autoprocessing all your sessions (by default). You can optionally do manual postprocessing with all this 'grunt work' preprocessing.
39
+ ## What is starbash?
40
+
41
+ <img src="https://raw.githubusercontent.com/geeksville/starbash/refs/heads/main/doc/img/icon.jpg" alt="Starbash: Astrophotography workflows simplified" width="30%" align="right" style="margin-bottom: 20px;">
42
+
43
+ * Automatic - with sensible defaults that you can change as needed. Just a few keystrokes to preprocess an entire repo of raw images.
44
+ * Easy - provides a 'seestar-like' autoprocessing all your sessions (by default). You can optionally do manual postprocessing with all this 'grunt work' preprocessing automated.
42
45
  * Fast<sup>1</sup> - even with large image repositories. Automatic master bias and flat generation. Automatic preprocessing/ stacking/background-elimination with reasonable defaults.
43
46
  * Multi-session - by default. So your workflows can stack from multiple nights (and still use the correct flats etc...).
44
47
  * Shareable - you can share/use recipes for image preprocessing flows. The eventual goal is a transition away from opaque burried scripts. Recipes can come from multiple repos and you or other orgs can host recipes.
@@ -49,7 +52,22 @@ A tool for automating/standardizing/sharing astrophotography workflows.
49
52
  <sub>**Caveats:**
50
53
  1. 'Fast' in terms of you 'just need to click run and magically (ahem) everything just happens.' But if you ask it to process many images it can take hours - just come back when it is done.</sub>
51
54
 
52
- <br clear="right">
55
+ ## What is starbash NOT
56
+
57
+ ### Not a new image processing tool (like Siril)
58
+ It is important to understand that Starbash is primarily a tool for **repeatable**, **sharable**, **semi-automated** workflows. It is tool agnostic and really just focuses on the relationship between tools, images and sessions. It builds upon the great work of existing tools (currently mainly Siril and Graxpert) so we can grow an ecosystem of recipes.
59
+
60
+ ### Not a set of scripts
61
+
62
+ It is more a tool for moving away from (sometimes long and complex) opaque scripts. "Recipes" are kinda like scripts except they are small and atomic and use dependencies to be automatically installed at the appropriate stage of workflows. But the actual operations performed by a recipe can be for any of the supported tools.
63
+
64
+ For instance: if you don't like a particular "stack" stage recipe you can swap out just that portion of the workflow for an alternate implementation. Or make your own and share it with others. (With full automatic versioning so that workflows hopefully always keep working/evolving)
65
+
66
+ Starbash understands FITS metadata and how to run tools based on that metadata, but the actual image transformations are entirely up to you and anyone who writes a recipe.
67
+
68
+ We provide a few example recipes to enable auto-selection of common workflows (see below for example links). But hopefully others will either add to these recipes or host their own recipe repos.
69
+
70
+ If you are familar with the software enginering tools "npm, make and git", the goal of this project is to provide an analogous sharable workflows for astrophotography.
53
71
 
54
72
  # Current status
55
73
 
@@ -68,21 +86,28 @@ If you are interested in alpha-testing we ❤️ you. This README should have e
68
86
  * Automatically performs **complete** preprocessing on OSC (broadband, narrowband, or dual Duo filter). i.e., gives you 'seestar-level' auto-preprocessing, so you only need to do the (optional) custom post-processing.
69
87
  * Uses Siril recipes for its pre-processing operations (support for Pixinsight-based recipes will probably be coming at some point...).
70
88
 
71
- ### From the alpha 2 (0.2.0) release (2025/12/12 ish)
72
- * Include a stretched 'thumbnail'(FIXME - link example thumbnail) jpg proof-of-concept render in the output directories
73
- * Generates a per-target [report/config file](FIXME - link example processed toml) which can be customized if the detected defaults or preprocessing are not what you want.
89
+ ### From the alpha 2 (0.2.0) release (2025/12/12)
90
+ * Include a stretched 'thumbnail'(FIXME/link/example/thumbnail) jpg proof-of-concept render in the output directories
91
+ * Generates a per-target [report/config file](doc/toml/example/processed-repo/example-m20.toml) which can be customized if the detected defaults or preprocessing are not what you want.
74
92
  * '[Recipes](https://github.com/geeksville/starbash-recipes)' are now user-editable - provides repeatable/human-[readable](doc/toml/example/processed-repo/example-m20.toml)/shareable descriptions of all processing steps. [example Siril OSC stacking](https://github.com/geeksville/starbash-recipes/blob/6d255f48591c4991ddc1168ffa5c38050a500771/osc/osc_simple.toml), [example Graxpert BGE](https://github.com/geeksville/starbash-recipes/blob/6d255f48591c4991ddc1168ffa5c38050a500771/graxpert/background.toml), [example thumbnail generation](https://github.com/geeksville/starbash-recipes/blob/6d255f48591c4991ddc1168ffa5c38050a500771/common/thumbnail.toml)...
75
93
  * Repos can be on the local disk or shared via HTTPS/GitHub/etc. This is particularly useful for recipe repos.
76
94
  * [Graxpert](https://graxpert.com/) based [recipe stages](https://github.com/geeksville/starbash-recipes/tree/main/graxpert) added (support for Pixinsight-based recipes will probably be coming at some point...).
77
95
 
78
96
  ## Features coming soon
79
97
 
80
- * Better recipe 'writers guide' documentation.
81
- * Support for mono-camera workflows (the alpha only has osc recipes).
98
+ * Recipe 'writers guide' documentation. Currently iterating based on usage reports 😄
99
+ * Support for mono-camera workflows (the alpha only includes osc recipes).
82
100
  * The target report can be used to auto-generate a human-friendly 'postable/shareable' report about that image.
83
101
  * Target reports are shareable so that you can request comments from others and others can rerender with different settings.
84
102
  * Namespaces for recipes are disambiguated to be globally unique
85
103
 
104
+ ## Features (possibly) coming eventually
105
+
106
+ * [IPFS](https://ipfs.tech/) based sharing of images and the workflows used to build those images (if you wish)
107
+ * Nice graph view of raw images, recipes and operations that contributed to a final image. Also possibly exposed via IPFS.
108
+ * Pixinsight?
109
+ * Autostakkert?
110
+
86
111
  See the [TODO](TODO.md) file for work items and approximate schedule.
87
112
 
88
113
  ## Support
@@ -206,8 +231,6 @@ If you don't want the automated processing you can still ask Starbash to prepare
206
231
 
207
232
  ## Supported telescope software
208
233
 
209
- FIXME explain FITS and directory paths
210
-
211
234
  * N.I.N.A. - tested, seems fairly okay.
212
235
  * Asiair - tested, seems fairly okay.
213
236
  * Seestar - tested, seems fairly okay.
@@ -221,27 +244,12 @@ Starbash is a tool agnostic workflow manager. But it wouldn't be possible witho
221
244
  * [Graxpert](https://graxpert.com/) - for background and noise elimination
222
245
  * [Python](https://www.python.org/) (you can add Python code to recipes if necessary)
223
246
 
224
- ## Supported tools (future?)
225
-
226
- * Pixinsight?
227
- * Autostakkert?
228
-
229
247
  ## Credits
230
248
  * Various reddit users who submitted anonymous crash reports from alpha 1
231
249
  * [@codegistics](https://github.com/codegistics) for kindly donating Dwarf3 test data and invaluable debugging assistance.
232
250
  * The developers of Siril and Graxpert - which are wonderful tools.
233
- * The [doit](https://pydoit.org/) automation building tool, which substantially simiplified this tool's development.
234
-
235
- ## Design
236
-
237
- FIXME - write this
238
-
239
- FIXME - what this tool is
240
- a way to avoid opaque script blobs that are tied to a particular tool.
241
- instead a way to make sharable/extendable workflows from atomic mini-tools
242
- A way to capture preprocessing steps used to create an image
243
- FIXME - what this tool isn't
244
- Influences from make, npm, github.
251
+ * The [doit](https://pydoit.org/) an **amazing** automation building tool, which substantially simiplified this tool's development.
252
+ * Any parts of the user interface that look good are probably due to the awesome [rich](https://github.com/Textualize/rich) library.
245
253
 
246
254
  ## Development
247
255
 
@@ -1,15 +1,17 @@
1
1
  # [Starbash](https://github.com/geeksville/starbash)
2
2
 
3
- <img src="https://raw.githubusercontent.com/geeksville/starbash/refs/heads/main/doc/img/icon.jpg" alt="Starbash: Astrophotography workflows simplified" width="30%" align="right" style="margin-bottom: 20px;">
4
-
5
3
  [![PyPI - Version](https://img.shields.io/pypi/v/starbash)](https://pypi.org/project/starbash/)
6
4
  [![Continuous Integration](https://github.com/geeksville/starbash/actions/workflows/ci.yml/badge.svg)](https://github.com/geeksville/starbash/actions/workflows/ci.yml)
7
5
  [![codecov](https://codecov.io/github/geeksville/starbash/graph/badge.svg?token=47RE10I7O1)](https://codecov.io/github/geeksville/starbash)
8
6
 
9
7
  A tool for automating/standardizing/sharing astrophotography workflows.
10
8
 
11
- * Automatic - with sensible defaults that you can change as needed.
12
- * Easy - provides a 'seestar-like' autoprocessing all your sessions (by default). You can optionally do manual postprocessing with all this 'grunt work' preprocessing.
9
+ ## What is starbash?
10
+
11
+ <img src="https://raw.githubusercontent.com/geeksville/starbash/refs/heads/main/doc/img/icon.jpg" alt="Starbash: Astrophotography workflows simplified" width="30%" align="right" style="margin-bottom: 20px;">
12
+
13
+ * Automatic - with sensible defaults that you can change as needed. Just a few keystrokes to preprocess an entire repo of raw images.
14
+ * Easy - provides a 'seestar-like' autoprocessing all your sessions (by default). You can optionally do manual postprocessing with all this 'grunt work' preprocessing automated.
13
15
  * Fast<sup>1</sup> - even with large image repositories. Automatic master bias and flat generation. Automatic preprocessing/ stacking/background-elimination with reasonable defaults.
14
16
  * Multi-session - by default. So your workflows can stack from multiple nights (and still use the correct flats etc...).
15
17
  * Shareable - you can share/use recipes for image preprocessing flows. The eventual goal is a transition away from opaque burried scripts. Recipes can come from multiple repos and you or other orgs can host recipes.
@@ -20,7 +22,22 @@ A tool for automating/standardizing/sharing astrophotography workflows.
20
22
  <sub>**Caveats:**
21
23
  1. 'Fast' in terms of you 'just need to click run and magically (ahem) everything just happens.' But if you ask it to process many images it can take hours - just come back when it is done.</sub>
22
24
 
23
- <br clear="right">
25
+ ## What is starbash NOT
26
+
27
+ ### Not a new image processing tool (like Siril)
28
+ It is important to understand that Starbash is primarily a tool for **repeatable**, **sharable**, **semi-automated** workflows. It is tool agnostic and really just focuses on the relationship between tools, images and sessions. It builds upon the great work of existing tools (currently mainly Siril and Graxpert) so we can grow an ecosystem of recipes.
29
+
30
+ ### Not a set of scripts
31
+
32
+ It is more a tool for moving away from (sometimes long and complex) opaque scripts. "Recipes" are kinda like scripts except they are small and atomic and use dependencies to be automatically installed at the appropriate stage of workflows. But the actual operations performed by a recipe can be for any of the supported tools.
33
+
34
+ For instance: if you don't like a particular "stack" stage recipe you can swap out just that portion of the workflow for an alternate implementation. Or make your own and share it with others. (With full automatic versioning so that workflows hopefully always keep working/evolving)
35
+
36
+ Starbash understands FITS metadata and how to run tools based on that metadata, but the actual image transformations are entirely up to you and anyone who writes a recipe.
37
+
38
+ We provide a few example recipes to enable auto-selection of common workflows (see below for example links). But hopefully others will either add to these recipes or host their own recipe repos.
39
+
40
+ If you are familar with the software enginering tools "npm, make and git", the goal of this project is to provide an analogous sharable workflows for astrophotography.
24
41
 
25
42
  # Current status
26
43
 
@@ -39,21 +56,28 @@ If you are interested in alpha-testing we ❤️ you. This README should have e
39
56
  * Automatically performs **complete** preprocessing on OSC (broadband, narrowband, or dual Duo filter). i.e., gives you 'seestar-level' auto-preprocessing, so you only need to do the (optional) custom post-processing.
40
57
  * Uses Siril recipes for its pre-processing operations (support for Pixinsight-based recipes will probably be coming at some point...).
41
58
 
42
- ### From the alpha 2 (0.2.0) release (2025/12/12 ish)
43
- * Include a stretched 'thumbnail'(FIXME - link example thumbnail) jpg proof-of-concept render in the output directories
44
- * Generates a per-target [report/config file](FIXME - link example processed toml) which can be customized if the detected defaults or preprocessing are not what you want.
59
+ ### From the alpha 2 (0.2.0) release (2025/12/12)
60
+ * Include a stretched 'thumbnail'(FIXME/link/example/thumbnail) jpg proof-of-concept render in the output directories
61
+ * Generates a per-target [report/config file](doc/toml/example/processed-repo/example-m20.toml) which can be customized if the detected defaults or preprocessing are not what you want.
45
62
  * '[Recipes](https://github.com/geeksville/starbash-recipes)' are now user-editable - provides repeatable/human-[readable](doc/toml/example/processed-repo/example-m20.toml)/shareable descriptions of all processing steps. [example Siril OSC stacking](https://github.com/geeksville/starbash-recipes/blob/6d255f48591c4991ddc1168ffa5c38050a500771/osc/osc_simple.toml), [example Graxpert BGE](https://github.com/geeksville/starbash-recipes/blob/6d255f48591c4991ddc1168ffa5c38050a500771/graxpert/background.toml), [example thumbnail generation](https://github.com/geeksville/starbash-recipes/blob/6d255f48591c4991ddc1168ffa5c38050a500771/common/thumbnail.toml)...
46
63
  * Repos can be on the local disk or shared via HTTPS/GitHub/etc. This is particularly useful for recipe repos.
47
64
  * [Graxpert](https://graxpert.com/) based [recipe stages](https://github.com/geeksville/starbash-recipes/tree/main/graxpert) added (support for Pixinsight-based recipes will probably be coming at some point...).
48
65
 
49
66
  ## Features coming soon
50
67
 
51
- * Better recipe 'writers guide' documentation.
52
- * Support for mono-camera workflows (the alpha only has osc recipes).
68
+ * Recipe 'writers guide' documentation. Currently iterating based on usage reports 😄
69
+ * Support for mono-camera workflows (the alpha only includes osc recipes).
53
70
  * The target report can be used to auto-generate a human-friendly 'postable/shareable' report about that image.
54
71
  * Target reports are shareable so that you can request comments from others and others can rerender with different settings.
55
72
  * Namespaces for recipes are disambiguated to be globally unique
56
73
 
74
+ ## Features (possibly) coming eventually
75
+
76
+ * [IPFS](https://ipfs.tech/) based sharing of images and the workflows used to build those images (if you wish)
77
+ * Nice graph view of raw images, recipes and operations that contributed to a final image. Also possibly exposed via IPFS.
78
+ * Pixinsight?
79
+ * Autostakkert?
80
+
57
81
  See the [TODO](TODO.md) file for work items and approximate schedule.
58
82
 
59
83
  ## Support
@@ -177,8 +201,6 @@ If you don't want the automated processing you can still ask Starbash to prepare
177
201
 
178
202
  ## Supported telescope software
179
203
 
180
- FIXME explain FITS and directory paths
181
-
182
204
  * N.I.N.A. - tested, seems fairly okay.
183
205
  * Asiair - tested, seems fairly okay.
184
206
  * Seestar - tested, seems fairly okay.
@@ -192,27 +214,12 @@ Starbash is a tool agnostic workflow manager. But it wouldn't be possible witho
192
214
  * [Graxpert](https://graxpert.com/) - for background and noise elimination
193
215
  * [Python](https://www.python.org/) (you can add Python code to recipes if necessary)
194
216
 
195
- ## Supported tools (future?)
196
-
197
- * Pixinsight?
198
- * Autostakkert?
199
-
200
217
  ## Credits
201
218
  * Various reddit users who submitted anonymous crash reports from alpha 1
202
219
  * [@codegistics](https://github.com/codegistics) for kindly donating Dwarf3 test data and invaluable debugging assistance.
203
220
  * The developers of Siril and Graxpert - which are wonderful tools.
204
- * The [doit](https://pydoit.org/) automation building tool, which substantially simiplified this tool's development.
205
-
206
- ## Design
207
-
208
- FIXME - write this
209
-
210
- FIXME - what this tool is
211
- a way to avoid opaque script blobs that are tied to a particular tool.
212
- instead a way to make sharable/extendable workflows from atomic mini-tools
213
- A way to capture preprocessing steps used to create an image
214
- FIXME - what this tool isn't
215
- Influences from make, npm, github.
221
+ * The [doit](https://pydoit.org/) an **amazing** automation building tool, which substantially simiplified this tool's development.
222
+ * Any parts of the user interface that look good are probably due to the awesome [rich](https://github.com/Textualize/rich) library.
216
223
 
217
224
  ## Development
218
225
 
@@ -1,6 +1,6 @@
1
1
  [tool.poetry]
2
2
  name = "starbash"
3
- version = "0.1.35"
3
+ version = "0.2.3"
4
4
  description = "A tool for automating/standardizing/sharing astrophotography workflows."
5
5
  authors = ["Kevin Hester <kevinh@geeksville.com>"]
6
6
  readme = "README.md"
@@ -25,11 +25,17 @@ sentry-sdk = "^2.42.1"
25
25
  update-checker = "^0.18.0"
26
26
  requests-cache = "^1.2.1"
27
27
  doit = "^0.36.0"
28
+ textual = "^6.8.0"
28
29
 
29
30
  # Note: to use graxpert from the local tree rather than pypi use:
30
31
  # graxpert = {path = "GraXpert", extras = ["cpuonly"], develop = true}
31
32
  graxpert = {version = "^3.2.0a1", extras = ["cpuonly"]}
32
33
 
34
+ # The following two libs are only needed for the experiment of running siril scripts directly...
35
+ # experimenting with siril-scripts/processing/VeraLux_HyperMetric_Stretch.py
36
+ #numpy = "2.2.6"
37
+ #pyqt6 = "^6.10.1"
38
+
33
39
  [tool.poetry.group.dev.dependencies]
34
40
  pytest = ">=8.4.2,<9.0.0"
35
41
  pytest-cov = "^6.0.0"
@@ -37,6 +43,7 @@ pytest-xdist = "^3.8.0"
37
43
  pre-commit = "^4.3.0"
38
44
  ruff = "^0.14.4"
39
45
  basedpyright = "^1.33.0"
46
+ textual-dev = "^1.8.0"
40
47
 
41
48
  # We don't currently use this text based sql client
42
49
  # harlequin = "^2.4.1"
@@ -56,7 +63,7 @@ markers = [
56
63
  # --tb=short shows shorter tracebacks
57
64
  # -rA shows summary of all test outcomes at end
58
65
  # --ignore excludes third-party test directories
59
- addopts = "-m 'not slow and not integration' -n auto --tb=short -rA --ignore=GraXpert"
66
+ addopts = "-m 'not slow and not integration' -n auto --tb=short -rA --ignore=GraXpert --ignore=textual --ignore=starbash-recipes"
60
67
 
61
68
  # Note: To limit captured output further, you can:
62
69
  # 1. Use --tb=line for minimal tracebacks
@@ -88,7 +95,24 @@ line-length = 100
88
95
  target-version = "py312"
89
96
 
90
97
  # Exclude a variety of commonly ignored directories
91
- exclude = [".git", ".venv", "__pycache__", "build", "dist"]
98
+ exclude = [".git", ".venv", "__pycache__", "build", "dist", "reference", "siril-scripts"]
99
+
100
+ [tool.ruff.format]
101
+ # Only format files in src/ and tests/ - exclude everything else
102
+ exclude = [
103
+ "doc/**",
104
+ "examples/**",
105
+ "siril-scripts/**",
106
+ "htmlcov/**",
107
+ "images/**",
108
+ "reference/**",
109
+ "starbash-recipes/**",
110
+ "test-data/**",
111
+ "GraXpert/**",
112
+ "textual/**",
113
+ "bin/**",
114
+ "*.py" # Exclude root-level Python files
115
+ ]
92
116
 
93
117
  [tool.ruff.lint]
94
118
  # Enable these rule sets
@@ -505,7 +505,12 @@ class Repo:
505
505
  """
506
506
  # Construct the full URL by joining the base URL with the filepath
507
507
  if filepath:
508
- url = self.url.rstrip("/") + "/" + filepath.lstrip("/")
508
+ # If the URL points to a .toml file, strip the filename to get the directory
509
+ base_url = self.url
510
+ if self._is_direct_toml_file():
511
+ # Strip the .toml filename to get the parent directory URL
512
+ base_url = base_url.rsplit("/", 1)[0]
513
+ url = base_url.rstrip("/") + "/" + filepath.lstrip("/")
509
514
  else:
510
515
  url = self.url
511
516
 
@@ -7,7 +7,7 @@ from rich.console import Console
7
7
 
8
8
  # Common type aliases for clarity
9
9
  type StageDict = dict[str, Any] # a processing stage definition from our toml
10
- type InputDef = dict[str, Any] # an input definition within a stage
10
+ type InputDef = dict[Any, Any] # an input definition within a stage
11
11
  type OutputDef = dict[str, Any] # an output definition within a stage
12
12
  type RequireDef = dict[str, Any] # a requires definition within an input
13
13
  type Metadata = dict[str, Any] # image metadata dictionary
@@ -47,9 +47,9 @@ def analytics_setup(allowed: bool = False, user_email: str | None = None) -> Non
47
47
  ], # This line removes the aggressive unhandled exception catcher
48
48
  integrations=[
49
49
  LoggingIntegration(
50
- level=starbash.log_filter_level, # Capture INFO and above as breadcrumbs
50
+ level=starbash.log_filter_level, # Capture INFO and above as breadcrumbs (used for exception reports)
51
51
  event_level=None, # Don't automatically convert error messages to sentry events
52
- sentry_logs_level=starbash.log_filter_level, # Capture INFO and above as logs
52
+ sentry_logs_level=logging.INFO, # Capture INFO and above as logs (general usage)
53
53
  ),
54
54
  ],
55
55
  )
@@ -85,7 +85,7 @@ def is_development_environment() -> bool:
85
85
  return False
86
86
 
87
87
 
88
- def analytics_exception(exc: Exception) -> bool:
88
+ def analytics_exception(exc: BaseException) -> bool:
89
89
  """Report an exception to the analytics service, if enabled.
90
90
  return True to suppress exception propagation/log messages"""
91
91
 
@@ -3,6 +3,7 @@ import logging
3
3
  import sys
4
4
  from importlib.metadata import version
5
5
  from pathlib import Path
6
+ from sqlite3 import OperationalError
6
7
  from string import Template
7
8
  from typing import Any
8
9
 
@@ -36,7 +37,7 @@ from starbash.database import (
36
37
  get_column_name,
37
38
  )
38
39
  from starbash.dwarf3 import extend_dwarf3_headers
39
- from starbash.exception import UserHandledError, raise_missing_repo
40
+ from starbash.exception import NonSoftwareError, UserHandledError, raise_missing_repo
40
41
  from starbash.linux import linux_init
41
42
  from starbash.os import symlink_or_copy
42
43
  from starbash.paths import get_user_config_dir, get_user_config_path
@@ -121,6 +122,28 @@ def copy_images_to_dir(images: list[ImageRow], output_dir: Path) -> None:
121
122
  console.print(f" [red]Errors: {error_count} files[/red]")
122
123
 
123
124
 
125
+ def remap_expected_errors(exc: BaseException | None) -> BaseException | None:
126
+ """Remap certain expected exceptions to UserHandledError for consistent handling."""
127
+
128
+ if exc is None:
129
+ return None
130
+
131
+ # Some OSErrors definitely don't indicate a code level bug...
132
+ expected_errors = [ "Read-only file system" ]
133
+
134
+ if isinstance(exc, OperationalError):
135
+ return NonSoftwareError(f"[red]Database IO error:[/red] {exc}")
136
+ elif isinstance(exc, FileNotFoundError):
137
+ return NonSoftwareError(f"[red]OS error:[/red] {exc}")
138
+ elif isinstance(exc, OSError):
139
+ exc_str = str(exc)
140
+ if any(err in exc_str for err in expected_errors):
141
+ return NonSoftwareError(f"[red]OS error:[/red] {exc}")
142
+ # Add more remappings as needed
143
+
144
+ return exc
145
+
146
+
124
147
  class Starbash:
125
148
  """The main Starbash application class."""
126
149
 
@@ -161,7 +184,8 @@ class Starbash:
161
184
  self._init_repos()
162
185
  self._init_analytics(cmd) # after init repos so we have user prefs
163
186
 
164
- logging.info("Starbash starting")
187
+ app_version = version("starbash")
188
+ logging.info(f"🚀 Starbash {app_version} starting!")
165
189
 
166
190
  check_version()
167
191
  self._init_aliases()
@@ -271,20 +295,38 @@ class Starbash:
271
295
  return self
272
296
 
273
297
  def __exit__(self, exc_type, exc, tb) -> bool:
298
+ from starbash import _is_test_env
274
299
  from starbash.exception import UserHandledError
275
300
 
301
+ exc = remap_expected_errors(exc)
302
+
276
303
  handled = False
277
304
  # Don't suppress typer.Exit - it's used for controlled exit codes
278
305
  if exc and not isinstance(exc, typer.Exit) and not isinstance(exc, KeyboardInterrupt):
279
- # For UserHandledError, call ask_user_handled() and don't suppress
280
- if isinstance(exc, UserHandledError):
281
- exc.ask_user_handled()
306
+ # For errors we expect, just print error message and exit cleanly
307
+ if isinstance(exc, NonSoftwareError):
308
+ # For UserHandledError, call ask_user_handled() and don't suppress
309
+ if isinstance(exc, UserHandledError):
310
+ exc.ask_user_handled()
311
+ else:
312
+ starbash.console.print(exc)
282
313
  self.close()
283
314
  # Raise typer.Exit to ensure proper exit code
284
315
  raise typer.Exit(code=1)
285
316
  else:
286
317
  handled = analytics_exception(exc)
287
- self.close()
318
+ self.close()
319
+ if not handled:
320
+ # Show the full exception for developers
321
+ starbash.console.print_exception(show_locals=False) # Locals are too verbose
322
+
323
+ # In test environments, let exceptions propagate naturally for better test diagnostics
324
+ if not _is_test_env:
325
+ # But in any case, make our app exit with an error code
326
+ raise typer.Exit(code=1)
327
+ else:
328
+ self.close()
329
+
288
330
  return handled
289
331
 
290
332
  def _add_session(self, header: dict) -> None:
@@ -439,7 +481,7 @@ class Starbash:
439
481
  absolute_path = repo.resolve_path(relative_path)
440
482
  image["abspath"] = str(absolute_path)
441
483
  else:
442
- logging.error(f"Repo not found for URL: {repo_url}, skipping image...")
484
+ raise UserHandledError(f"Repo not found for URL: {repo_url}, session skipped.")
443
485
 
444
486
  return image
445
487
 
@@ -14,6 +14,7 @@ from starbash.commands.__init__ import (
14
14
  from starbash.commands.select import selection_by_number
15
15
  from starbash.database import SessionRow
16
16
  from starbash.doit import FileInfo
17
+ from starbash.paths import get_user_config_path
17
18
  from starbash.processed_target import ProcessedTarget
18
19
  from starbash.processing import Processing, ProcessingResult
19
20
  from starbash.rich import to_rich_link
@@ -110,7 +111,9 @@ def print_results(
110
111
  from rich.table import Table
111
112
 
112
113
  if not results:
113
- console.print(f"[yellow]{title}: No results, do you have a target selected?[/yellow]")
114
+ console.print(
115
+ f"[yellow]{title}: No results, do you have a target selected? If this is your first time here run 'sb user setup'[/yellow]"
116
+ )
114
117
  return
115
118
 
116
119
  table = Table(title=title, show_header=True, header_style=TABLE_HEADER_STYLE)
@@ -212,18 +215,25 @@ def auto(
212
215
  import starbash
213
216
 
214
217
  starbash.process_masters = False
218
+
219
+ # Users might run "process auto" as their first command without reading any docs...
220
+ if not get_user_config_path().exists():
221
+ from starbash import console
222
+
223
+ console.print("[red]No app setup found.[/red] Please run 'sb user setup'.")
224
+ raise typer.Exit(1)
225
+
215
226
  with Starbash("process.auto") as sb:
216
227
  with Processing(sb) as proc:
217
228
  from starbash import console
218
229
 
219
230
  if session_num is not None:
220
231
  console.print(
221
- f"[read]Session number base filtering not yet implemented: {session_num}...[/red]"
232
+ f"[red]Session number base filtering not yet implemented: {session_num}...[/red]"
222
233
  )
223
234
  else:
224
235
  console.print("[yellow]Auto-processing all selected sessions...[/yellow]")
225
236
 
226
- try:
227
237
  results = proc.run_all_stages()
228
238
 
229
239
  title = "Autoprocessed"
@@ -237,10 +247,6 @@ def auto(
237
247
 
238
248
  print_results(title, results, console)
239
249
 
240
- except Exception:
241
- console.print_exception(show_locals=True)
242
- raise typer.Exit(code=1)
243
-
244
250
 
245
251
  @app.command(
246
252
  context_settings={"allow_extra_args": True, "ignore_unknown_options": True},
@@ -152,6 +152,7 @@ def _ask_user_config(sb: Starbash) -> None:
152
152
 
153
153
 
154
154
  def do_reinit(sb: Starbash) -> None:
155
+ """Do guided 1st time setup for starbash."""
155
156
  from starbash import console
156
157
 
157
158
  console.print()
@@ -177,11 +178,9 @@ def do_reinit(sb: Starbash) -> None:
177
178
  Recommended next steps (to get your first auto-generated images):
178
179
  1. Add your source raw image repositories (starbash will only READ from these):
179
180
  [cyan]sb repo add /path/to/your/raw_images[/cyan]
180
- 2. Ask starbash to auto-generate 'master' darks, biases and flats:
181
- [cyan]sb process masters[/cyan]
182
- 3. Process your images using automated workflows:
181
+ 2. Process your images using automated workflows:
183
182
  [cyan]sb process auto[/cyan]
184
- 4. (Highly recommended) Tell your shell to auto-complete starbash commands:
183
+ 3. (Highly recommended) Tell your shell to auto-complete starbash commands:
185
184
  [cyan]sb shell-complete --install-completion[/cyan]
186
185
 
187
186
  This project is currently very 'alpha' but we are eager to have it work for you.
@@ -252,11 +252,10 @@ class ToolAction(BaseAction):
252
252
  self.result = self.tool.run(
253
253
  self.commands, context=context, cwd=self.cwd, log_out=logfile, **self.parameters
254
254
  )
255
- except ValueError as e:
255
+ except Exception as e:
256
256
  # We pass back any exceptions in task.meta - so that our ConsoleReporter can pick them up (doit normally strips exceptions)
257
257
  self.task.meta["exception"] = e
258
258
  return TaskFailed("tool failed")
259
- # raise e # Let doit do its normal exception handling though
260
259
 
261
260
  self.values = {} # doit requires this attribute to be set
262
261
 
@@ -1,7 +1,17 @@
1
1
  from typing import Any, NoReturn
2
2
 
3
3
 
4
- class UserHandledError(ValueError):
4
+ class NonSoftwareError(Exception):
5
+ """An error outside the control of the software, exit the app with an error code, but no need to
6
+ report it as a software bug.
7
+
8
+ Used for OS errors etc after we've determined we can't do anything more useful."""
9
+
10
+ def __rich__(self) -> Any:
11
+ return self.__str__() # At least this is something readable...
12
+
13
+
14
+ class UserHandledError(NonSoftwareError):
5
15
  """An exception that terminates processing of the current file, but we want to help the user fix the problem."""
6
16
 
7
17
  def ask_user_handled(self) -> bool:
@@ -14,9 +24,6 @@ class UserHandledError(ValueError):
14
24
  console.print(f"Error: {self}")
15
25
  return False
16
26
 
17
- def __rich__(self) -> Any:
18
- return self.__str__() # At least this is something readable...
19
-
20
27
 
21
28
  def raise_missing_repo(kind: str) -> NoReturn:
22
29
  """Raise a UserHandledError indicating that a repository of the given kind is missing."""
@@ -64,8 +64,13 @@ def get_user_data_dir() -> Path:
64
64
 
65
65
 
66
66
  def get_user_cache_dir() -> Path:
67
- """Get the user cache directory. Returns test override if set, otherwise the real user directory."""
68
- dir_to_use = _override_cache_dir if _override_cache_dir is not None else cache_dir
67
+ """Get the user cache directory. Returns test override if set, otherwise checks STARBASH_CACHE_DIR env var, otherwise the real user directory."""
68
+ if _override_cache_dir is not None:
69
+ dir_to_use = _override_cache_dir
70
+ elif env_cache_dir := os.getenv("STARBASH_CACHE_DIR"):
71
+ dir_to_use = Path(env_cache_dir)
72
+ else:
73
+ dir_to_use = cache_dir
69
74
  os.makedirs(dir_to_use, exist_ok=True)
70
75
  return dir_to_use
71
76