base-loom-server 0.2__tar.gz → 0.3.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.
Files changed (57) hide show
  1. {base_loom_server-0.2 → base_loom_server-0.3.0}/.gitignore +2 -1
  2. {base_loom_server-0.2 → base_loom_server-0.3.0}/.pre-commit-config.yaml +4 -4
  3. base_loom_server-0.3.0/PKG-INFO +126 -0
  4. base_loom_server-0.3.0/README.md +104 -0
  5. {base_loom_server-0.2 → base_loom_server-0.3.0}/pyproject.toml +10 -19
  6. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/app_runner.py +44 -3
  7. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/base_loom_server.py +14 -10
  8. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/client_replies.py +2 -4
  9. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/display.html_template +1 -1
  10. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/display.js +7 -7
  11. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/example_loom_server.py +1 -7
  12. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/example_mock_loom.py +0 -2
  13. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/pattern_database.py +68 -21
  14. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/reduced_pattern.py +44 -40
  15. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/testutils.py +19 -17
  16. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/version.py +1 -1
  17. base_loom_server-0.3.0/src/base_loom_server.egg-info/PKG-INFO +126 -0
  18. base_loom_server-0.3.0/src/base_loom_server.egg-info/requires.txt +9 -0
  19. {base_loom_server-0.2 → base_loom_server-0.3.0}/tests/test_pattern_database.py +28 -13
  20. {base_loom_server-0.2 → base_loom_server-0.3.0}/tests/test_reduced_pattern.py +7 -5
  21. base_loom_server-0.2/PKG-INFO +0 -79
  22. base_loom_server-0.2/README.md +0 -58
  23. base_loom_server-0.2/src/base_loom_server.egg-info/PKG-INFO +0 -79
  24. base_loom_server-0.2/src/base_loom_server.egg-info/requires.txt +0 -8
  25. {base_loom_server-0.2 → base_loom_server-0.3.0}/LICENSE.txt +0 -0
  26. {base_loom_server-0.2 → base_loom_server-0.3.0}/setup.cfg +0 -0
  27. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/__init__.py +0 -0
  28. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/base_mock_loom.py +0 -0
  29. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/constants.py +0 -0
  30. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/display.css +0 -0
  31. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/favicon-32x32.png +0 -0
  32. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/locales/README.md +0 -0
  33. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/locales/default.json +0 -0
  34. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/locales/fr.json +0 -0
  35. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/main.py +0 -0
  36. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/mock_streams.py +0 -0
  37. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/py.typed +0 -0
  38. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/many color liftplan and zeros.dtx +0 -0
  39. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/many color liftplan and zeros.wif +0 -0
  40. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/many color multiple treadles and zeros.dtx +0 -0
  41. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/many color multiple treadles and zeros.wif +0 -0
  42. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/many color single treadles.dtx +0 -0
  43. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/many color single treadles.wif +0 -0
  44. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/two color liftplan.dtx +0 -0
  45. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/two color liftplan.wif +0 -0
  46. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/two color multiple treadles.dtx +0 -0
  47. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/two color multiple treadles.wif +0 -0
  48. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/two color single treadles.dtx +0 -0
  49. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server/test_data/two color single treadles.wif +0 -0
  50. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server.egg-info/SOURCES.txt +0 -0
  51. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server.egg-info/dependency_links.txt +0 -0
  52. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server.egg-info/entry_points.txt +0 -0
  53. {base_loom_server-0.2 → base_loom_server-0.3.0}/src/base_loom_server.egg-info/top_level.txt +0 -0
  54. {base_loom_server-0.2 → base_loom_server-0.3.0}/tests/test_loom_server.py +0 -0
  55. {base_loom_server-0.2 → base_loom_server-0.3.0}/tests/test_mock_loom.py +0 -0
  56. {base_loom_server-0.2 → base_loom_server-0.3.0}/tests/test_mock_streams.py +0 -0
  57. {base_loom_server-0.2 → base_loom_server-0.3.0}/tests/test_version.py +0 -0
@@ -1,5 +1,6 @@
1
1
  __pycache__
2
2
  .coverage
3
3
  *.egg-info
4
- dist
4
+ build/
5
+ dist/
5
6
  version.py
@@ -1,13 +1,13 @@
1
1
  repos:
2
2
  - repo: https://github.com/pre-commit/pre-commit-hooks
3
- rev: v4.6.0
3
+ rev: v5.0.0
4
4
  hooks:
5
5
  - id: check-yaml
6
6
  exclude: conda/meta.yaml
7
7
  - id: check-xml
8
8
 
9
9
  - repo: https://github.com/psf/black
10
- rev: 24.8.0
10
+ rev: 25.1.0
11
11
  hooks:
12
12
  - id: black
13
13
 
@@ -17,12 +17,12 @@ repos:
17
17
  - id: flake8
18
18
 
19
19
  - repo: https://github.com/pycqa/isort
20
- rev: 5.13.2
20
+ rev: 6.0.0
21
21
  hooks:
22
22
  - id: isort
23
23
  name: isort (python)
24
24
 
25
25
  - repo: https://github.com/pre-commit/mirrors-mypy
26
- rev: v1.11.2
26
+ rev: v1.15.0
27
27
  hooks:
28
28
  - id: mypy
@@ -0,0 +1,126 @@
1
+ Metadata-Version: 2.2
2
+ Name: base_loom_server
3
+ Version: 0.3.0
4
+ Summary: Base package for web servers that control dobby multi-shaft looms
5
+ Author-email: Russell Owen <r3owen@gmail.com>
6
+ Project-URL: Homepage, https://github.com/r-owen/base_loom_server
7
+ Project-URL: Issues, https://github.com/r-owen/base_loom_server/issues
8
+ Classifier: Programming Language :: Python :: 3
9
+ Classifier: License :: OSI Approved :: MIT License
10
+ Classifier: Operating System :: OS Independent
11
+ Requires-Python: >=3.11
12
+ Description-Content-Type: text/markdown
13
+ License-File: LICENSE.txt
14
+ Requires-Dist: aiosqlite>=0.20
15
+ Requires-Dist: dtx_to_wif~=3.0
16
+ Requires-Dist: fastapi[standard]~=0.115
17
+ Requires-Dist: pyserial-asyncio~=0.6
18
+ Provides-Extra: dev
19
+ Requires-Dist: pre-commit~=4.0; extra == "dev"
20
+ Requires-Dist: pytest~=8.3; extra == "dev"
21
+ Requires-Dist: pytest-asyncio~=0.25; extra == "dev"
22
+
23
+ # Base package for web servers that control dobby multi-shaft looms
24
+
25
+ Such web servers are intended to allow you to control your loom from any phone, tablet or other device that has wifi and a web browser.
26
+
27
+ Used by [seguin_loom_server](<https://pypi.org/project/seguin-loom-server/)>)
28
+ and [toika_loom_server](https://pypi.org/project/toika-loom-server/).
29
+
30
+ ## Installing this Package
31
+
32
+ You should only have to install this package if you want to examine or modify it.
33
+ If you are installing a loom driver such as
34
+ such as [seguin_loom_server](<https://pypi.org/project/seguin-loom-server/)>)
35
+ or [toika_loom_server](https://pypi.org/project/toika-loom-server/),
36
+ then you only need to install that package.
37
+ Doing so will pull in all dependencies.
38
+
39
+ Assuming you still want your own installation of base_loom_server:
40
+
41
+ * Install [Python](https://www.python.org/downloads/) 3.11 or later on the computer.
42
+
43
+ * If you are using python for other things, you may wish to make a virtual environment
44
+ dedicated to your loom server software. Look up "python virtual environment" on line.
45
+
46
+ * Install this [base_loom_server](https://pypi.org/project/base-loom-server/) package on the computer with command:
47
+
48
+ * On Raspberry Pi: **sudo pip install base_loom_server**
49
+ * On most other computers: **pip install base_loom_server**
50
+
51
+ If you have a Raspberry Pi then you have three choices for installation:
52
+
53
+ * Use sudo for all pip install commands. This is simplest.
54
+ * Add "~/.local/bin" to your PATH. You can read about that on line.
55
+ * Prefix the run command with ".local/bin", e.g. **.local/bin/run_example_loom**.
56
+
57
+ ## Using this Package to Write a Loom Server
58
+
59
+ * Write a subclass of `BaseMockLoom` that emulates your loom.
60
+ Two examples are `ExampleMockLoom` in this package and `MockLoom`
61
+ in [toika_loom_server](https://pypi.org/project/toika-loom-server/).
62
+
63
+ * Write a subclass of `BaseLoomServer` that talks to the loom.
64
+ Two examples are `ExampleLoomServer` in this package and `LoomServer`
65
+ in [toika_loom_server](https://pypi.org/project/toika-loom-server/).
66
+
67
+ * Write a `main.py` like the one in this package, to run your loom server.
68
+
69
+ * Copy `tests/test_mock_loom.py` and modify it to suit your mock loom.
70
+
71
+ * The unit tests for your loom server should be able to use `testutils.BaseTestLoomServer`, as `tests/test_loom_server.py` does.
72
+
73
+ * Write a `pyproject.toml` like the one for [toika_loom_server](https://pypi.org/project/toika-loom-server/).
74
+
75
+ ## Remembering Patterns
76
+
77
+ The web server keeps track of the most recent 25 patterns you have used in a database
78
+ (including the most recent pick number and number of repeats, which are restored when you select a pattern).
79
+ The patterns in the database are displayed in the pattern menu.
80
+ If you shut down the server or there is a power failure, all this information should be retained.
81
+
82
+ You can reset the database by starting the server with the **--reset-db** argument.
83
+ You must reset the database if you upgrade this base_loom_server package and the new database format is incompatible
84
+ (in which case the server will fail at startup).
85
+ You may also want to reset the database if you are weaving a new project and don't want to see any of the saved patterns.
86
+
87
+ ## Developer Tips
88
+
89
+ * Download the source code from [github](https://github.com/r-owen/base_loom_server.git),
90
+ or make a fork and git clone that.
91
+
92
+ * Inside the directory, issue the following commands:
93
+
94
+ * **pip install -e .'[dev]'** (the single quotes are required in zsh, but not in bash)
95
+ to make an "editable installation" of the package.
96
+ An editable installation runs from the source code,
97
+ so changes you make to the source are used when you run or test the code,
98
+ without the need to reinstall the package.
99
+ **'[dev]'** installs development-related packages such as pytest
100
+ (see the file `pyproject.toml` for the full list).
101
+
102
+ * **pre-commit install** to activate the pre-commit hooks.
103
+
104
+ * **pytest** to test your installation.
105
+
106
+ * You may run an example loom server with: **run_example_loom mock**.
107
+ Please only specify the **mock** serial port; connecting it to a real loom will not work
108
+ (`ExampleMockLoom` is loosely based on a Séguin loom, but is not compatible).
109
+
110
+ **run_example_loom mock** also accepts these command-line arguments:
111
+
112
+ * **--reset-db** Reset the pattern database. Try this if you think the database is corrupted.
113
+
114
+ * **--verbose** Print more diagnostic information.
115
+
116
+ Note that the example loom server uses the same pattern database as
117
+ [seguin_loom_server](<https://pypi.org/project/seguin-loom-server/)>)
118
+ and [toika_loom_server](https://pypi.org/project/toika-loom-server/).
119
+
120
+ * To run mypy run: ***MYPYPATH=src mypy .***. This avoids complaints about module name ambiguity.
121
+
122
+ * In mock mode the web page shows a few extra controls for debugging.
123
+
124
+ * Warning: the web server's automatic reload feature, which reloads Python code whenever you save changes, *does not work* with this software.
125
+ Instead you have to kill the web server by typing control-C several times, until you get a terminal prompt, then run the server again.
126
+ This may be a bug in uvicorn; see [this discussion](https://github.com/encode/uvicorn/discussions/2075) for more information.
@@ -0,0 +1,104 @@
1
+ # Base package for web servers that control dobby multi-shaft looms
2
+
3
+ Such web servers are intended to allow you to control your loom from any phone, tablet or other device that has wifi and a web browser.
4
+
5
+ Used by [seguin_loom_server](<https://pypi.org/project/seguin-loom-server/)>)
6
+ and [toika_loom_server](https://pypi.org/project/toika-loom-server/).
7
+
8
+ ## Installing this Package
9
+
10
+ You should only have to install this package if you want to examine or modify it.
11
+ If you are installing a loom driver such as
12
+ such as [seguin_loom_server](<https://pypi.org/project/seguin-loom-server/)>)
13
+ or [toika_loom_server](https://pypi.org/project/toika-loom-server/),
14
+ then you only need to install that package.
15
+ Doing so will pull in all dependencies.
16
+
17
+ Assuming you still want your own installation of base_loom_server:
18
+
19
+ * Install [Python](https://www.python.org/downloads/) 3.11 or later on the computer.
20
+
21
+ * If you are using python for other things, you may wish to make a virtual environment
22
+ dedicated to your loom server software. Look up "python virtual environment" on line.
23
+
24
+ * Install this [base_loom_server](https://pypi.org/project/base-loom-server/) package on the computer with command:
25
+
26
+ * On Raspberry Pi: **sudo pip install base_loom_server**
27
+ * On most other computers: **pip install base_loom_server**
28
+
29
+ If you have a Raspberry Pi then you have three choices for installation:
30
+
31
+ * Use sudo for all pip install commands. This is simplest.
32
+ * Add "~/.local/bin" to your PATH. You can read about that on line.
33
+ * Prefix the run command with ".local/bin", e.g. **.local/bin/run_example_loom**.
34
+
35
+ ## Using this Package to Write a Loom Server
36
+
37
+ * Write a subclass of `BaseMockLoom` that emulates your loom.
38
+ Two examples are `ExampleMockLoom` in this package and `MockLoom`
39
+ in [toika_loom_server](https://pypi.org/project/toika-loom-server/).
40
+
41
+ * Write a subclass of `BaseLoomServer` that talks to the loom.
42
+ Two examples are `ExampleLoomServer` in this package and `LoomServer`
43
+ in [toika_loom_server](https://pypi.org/project/toika-loom-server/).
44
+
45
+ * Write a `main.py` like the one in this package, to run your loom server.
46
+
47
+ * Copy `tests/test_mock_loom.py` and modify it to suit your mock loom.
48
+
49
+ * The unit tests for your loom server should be able to use `testutils.BaseTestLoomServer`, as `tests/test_loom_server.py` does.
50
+
51
+ * Write a `pyproject.toml` like the one for [toika_loom_server](https://pypi.org/project/toika-loom-server/).
52
+
53
+ ## Remembering Patterns
54
+
55
+ The web server keeps track of the most recent 25 patterns you have used in a database
56
+ (including the most recent pick number and number of repeats, which are restored when you select a pattern).
57
+ The patterns in the database are displayed in the pattern menu.
58
+ If you shut down the server or there is a power failure, all this information should be retained.
59
+
60
+ You can reset the database by starting the server with the **--reset-db** argument.
61
+ You must reset the database if you upgrade this base_loom_server package and the new database format is incompatible
62
+ (in which case the server will fail at startup).
63
+ You may also want to reset the database if you are weaving a new project and don't want to see any of the saved patterns.
64
+
65
+ ## Developer Tips
66
+
67
+ * Download the source code from [github](https://github.com/r-owen/base_loom_server.git),
68
+ or make a fork and git clone that.
69
+
70
+ * Inside the directory, issue the following commands:
71
+
72
+ * **pip install -e .'[dev]'** (the single quotes are required in zsh, but not in bash)
73
+ to make an "editable installation" of the package.
74
+ An editable installation runs from the source code,
75
+ so changes you make to the source are used when you run or test the code,
76
+ without the need to reinstall the package.
77
+ **'[dev]'** installs development-related packages such as pytest
78
+ (see the file `pyproject.toml` for the full list).
79
+
80
+ * **pre-commit install** to activate the pre-commit hooks.
81
+
82
+ * **pytest** to test your installation.
83
+
84
+ * You may run an example loom server with: **run_example_loom mock**.
85
+ Please only specify the **mock** serial port; connecting it to a real loom will not work
86
+ (`ExampleMockLoom` is loosely based on a Séguin loom, but is not compatible).
87
+
88
+ **run_example_loom mock** also accepts these command-line arguments:
89
+
90
+ * **--reset-db** Reset the pattern database. Try this if you think the database is corrupted.
91
+
92
+ * **--verbose** Print more diagnostic information.
93
+
94
+ Note that the example loom server uses the same pattern database as
95
+ [seguin_loom_server](<https://pypi.org/project/seguin-loom-server/)>)
96
+ and [toika_loom_server](https://pypi.org/project/toika-loom-server/).
97
+
98
+ * To run mypy run: ***MYPYPATH=src mypy .***. This avoids complaints about module name ambiguity.
99
+
100
+ * In mock mode the web page shows a few extra controls for debugging.
101
+
102
+ * Warning: the web server's automatic reload feature, which reloads Python code whenever you save changes, *does not work* with this software.
103
+ Instead you have to kill the web server by typing control-C several times, until you get a terminal prompt, then run the server again.
104
+ This may be a bug in uvicorn; see [this discussion](https://github.com/encode/uvicorn/discussions/2075) for more information.
@@ -11,9 +11,10 @@ dynamic = ["version"]
11
11
  description = "Base package for web servers that control dobby multi-shaft looms"
12
12
  readme = "README.md"
13
13
  dependencies = [
14
- "fastapi >= 0.115",
15
- "dtx_to_wif >= 3.0",
16
- "pyserial-asyncio >= 0.6",
14
+ "aiosqlite >= 0.20",
15
+ "dtx_to_wif ~= 3.0",
16
+ "fastapi[standard] ~= 0.115",
17
+ "pyserial-asyncio ~= 0.6",
17
18
  ]
18
19
  authors = [
19
20
  { name="Russell Owen", email="r3owen@gmail.com" },
@@ -27,22 +28,9 @@ requires-python = ">=3.11"
27
28
 
28
29
  [project.optional-dependencies]
29
30
  dev = [
30
- "pre-commit >= 3.8",
31
- "pytest >= 8.3",
32
- "pytest-asyncio >= 0.24",
33
- ]
34
-
35
- # Needed due to including package data below
36
- [tool.setuptools.packages.find]
37
- where = ["src"]
38
-
39
- [tool.setuptools.package-data]
40
- "base_loom_server" = [
41
- "py.typed",
42
- "display.css",
43
- "display.html_template",
44
- "display.js",
45
- "favicon-32x32.png"
31
+ "pre-commit ~= 4.0",
32
+ "pytest ~= 8.3",
33
+ "pytest-asyncio ~= 0.25",
46
34
  ]
47
35
 
48
36
  [project.scripts]
@@ -65,3 +53,6 @@ write_to_template = """
65
53
  __all__ = ["__version__"]
66
54
  __version__ = "{version}"
67
55
  """
56
+
57
+ [tool.mypy]
58
+ explicit_package_bases = "True"
@@ -19,6 +19,30 @@ LOCALE_FILES = PKG_FILES.joinpath("locales")
19
19
 
20
20
 
21
21
  class AppRunner:
22
+ """Run the loom server application.
23
+
24
+ This contains the web server's endpoints,
25
+ the lifespan context manager,
26
+ and a method to create the argument parser.
27
+
28
+ In order to use this you *must* create an instance on import
29
+ (i.e. at the module level), typically in `main.py'.
30
+ If you defer creation, the web server will not see the endpoints!
31
+ See ``main.py`` for an example.
32
+
33
+ Parameters
34
+ ----------
35
+ app : FastAPI
36
+ The application, generated with ``app = FastAPI()``
37
+ server_class : Type[BaseLoomServer]
38
+ Your loom server class (NOT an instance, but the class itself).
39
+ favicon : bytes
40
+ A 32x32 or so favicon. None if empty.
41
+ app_package_name : the name of the python package for your loom server,
42
+ e.g. "toika_loom_server". This is used by the `run` method,
43
+ as an argument to `uvicorn.run`.
44
+ """
45
+
22
46
  def __init__(
23
47
  self,
24
48
  app: FastAPI,
@@ -52,9 +76,11 @@ class AppRunner:
52
76
  async def get_wrapper():
53
77
  return await self.get()
54
78
 
55
- @router.get("/favicon.ico", include_in_schema=False)
56
- async def get_favicon():
57
- return await self.get_favicon()
79
+ if self.favicon:
80
+
81
+ @router.get("/favicon.ico", include_in_schema=False)
82
+ async def get_favicon():
83
+ return await self.get_favicon()
58
84
 
59
85
  @router.websocket("/ws")
60
86
  async def websocket_endpoint_wrapper(websocket: WebSocket):
@@ -63,6 +89,10 @@ class AppRunner:
63
89
  app.include_router(router)
64
90
 
65
91
  def create_argument_parser(self) -> argparse.ArgumentParser:
92
+ """Create the argument parser.
93
+
94
+ Subclasses may override this to add more options.
95
+ """
66
96
  parser = argparse.ArgumentParser()
67
97
  parser.add_argument(
68
98
  "serial_port",
@@ -98,6 +128,13 @@ class AppRunner:
98
128
 
99
129
  @asynccontextmanager
100
130
  async def lifespan(self, app: FastAPI) -> AsyncGenerator[None, FastAPI]:
131
+ """Lifespan context manager for fastAPI.
132
+
133
+ Load the translation dict and create the sole instance of
134
+ the loom server class. That loom server instance persists
135
+ for the entire time the web server is running. This is because
136
+ the loom server speaks to one loom and serves at most one user.
137
+ """
101
138
  self.translation_dict = self.get_translation_dict()
102
139
 
103
140
  parser = self.create_argument_parser()
@@ -138,6 +175,7 @@ class AppRunner:
138
175
  return translation_dict
139
176
 
140
177
  async def get(self) -> HTMLResponse:
178
+ """Endpoint to get the main page."""
141
179
  display_html_template = PKG_FILES.joinpath("display.html_template").read_text()
142
180
 
143
181
  display_css = PKG_FILES.joinpath("display.css").read_text()
@@ -164,13 +202,16 @@ class AppRunner:
164
202
  return HTMLResponse(display_html)
165
203
 
166
204
  async def get_favicon(self) -> Response:
205
+ """Endpoint to get the favicon"""
167
206
  return Response(content=self.favicon, media_type="image/x-icon")
168
207
 
169
208
  async def websocket_endpoint(self, websocket: WebSocket) -> None:
209
+ """Websocket endpoint."""
170
210
  assert self.loom_server is not None
171
211
  await self.loom_server.run_client(websocket=websocket)
172
212
 
173
213
  def run(self, host="0.0.0.0", port=8000, log_level="info", reload=True) -> None:
214
+ """Parse command-line arguments and run the web server."""
174
215
  # Handle the help argument and also catch parsing errors right away
175
216
  arg_parser = self.create_argument_parser()
176
217
  arg_parser.parse_args()
@@ -119,7 +119,7 @@ class BaseLoomServer:
119
119
  self.done_task: asyncio.Future = asyncio.Future()
120
120
  self.current_pattern: ReducedPattern | None = None
121
121
  self.jump_pick = client_replies.JumpPickNumber(
122
- pick_number=None, repeat_number=None
122
+ pick_number=None, weaving_repeat_number=None
123
123
  )
124
124
  self.weave_forward = True
125
125
  self.loom_error_flag = False
@@ -309,7 +309,7 @@ class BaseLoomServer:
309
309
  If True then report JumpPickNumber, even if it has not changed.
310
310
  """
311
311
  null_jump_pick = client_replies.JumpPickNumber(
312
- pick_number=None, repeat_number=None
312
+ pick_number=None, weaving_repeat_number=None
313
313
  )
314
314
  do_report = force_output or self.jump_pick != null_jump_pick
315
315
  self.jump_pick = null_jump_pick
@@ -338,10 +338,12 @@ class BaseLoomServer:
338
338
  def increment_pick_number(self) -> int:
339
339
  """Increment pick_number in the specified direction.
340
340
 
341
- Increment repeat_number as well, if appropriate.
341
+ Increment weaving_repeat_number as well, if appropriate.
342
342
 
343
- Return the new pick number. This will be 0 if repeat_number changed,
344
- or if unweaving and repeat_number would be decremented to 0.
343
+ Return the new pick number. This will be 0 if
344
+ weaving_repeat_number changed,
345
+ or if unweaving and weaving_repeat_number
346
+ would be decremented to 0.
345
347
  """
346
348
  if self.current_pattern is None:
347
349
  return 0
@@ -405,7 +407,7 @@ class BaseLoomServer:
405
407
 
406
408
  self.jump_pick = client_replies.JumpPickNumber(
407
409
  pick_number=command.pick_number,
408
- repeat_number=command.repeat_number,
410
+ weaving_repeat_number=command.weaving_repeat_number,
409
411
  )
410
412
  await self.report_jump_pick_number()
411
413
 
@@ -530,8 +532,10 @@ class BaseLoomServer:
530
532
  self.current_pattern.set_current_pick_number(new_pick_number)
531
533
  else:
532
534
  new_pick_number = self.increment_pick_number()
533
- if self.jump_pick.repeat_number is not None:
534
- self.current_pattern.repeat_number = self.jump_pick.repeat_number
535
+ if self.jump_pick.weaving_repeat_number is not None:
536
+ self.current_pattern.weaving_repeat_number = (
537
+ self.jump_pick.weaving_repeat_number
538
+ )
535
539
  pick = self.current_pattern.get_current_pick()
536
540
  await self.write_shafts_to_loom(pick)
537
541
  await self.clear_jump_pick()
@@ -624,11 +628,11 @@ class BaseLoomServer:
624
628
  await self.pattern_db.update_pick_number(
625
629
  pattern_name=self.current_pattern.name,
626
630
  pick_number=self.current_pattern.pick_number,
627
- repeat_number=self.current_pattern.repeat_number,
631
+ weaving_repeat_number=self.current_pattern.weaving_repeat_number,
628
632
  )
629
633
  reply = client_replies.CurrentPickNumber(
630
634
  pick_number=self.current_pattern.pick_number,
631
- repeat_number=self.current_pattern.repeat_number,
635
+ weaving_repeat_number=self.current_pattern.weaving_repeat_number,
632
636
  )
633
637
  await self.write_to_client(reply)
634
638
 
@@ -1,5 +1,3 @@
1
- from __future__ import annotations
2
-
3
1
  import dataclasses
4
2
  import enum
5
3
 
@@ -45,7 +43,7 @@ class CurrentPickNumber:
45
43
 
46
44
  type: str = dataclasses.field(init=False, default="CurrentPickNumber")
47
45
  pick_number: int
48
- repeat_number: int
46
+ weaving_repeat_number: int
49
47
 
50
48
 
51
49
  @dataclasses.dataclass
@@ -54,7 +52,7 @@ class JumpPickNumber:
54
52
 
55
53
  type: str = dataclasses.field(init=False, default="JumpPickNumber")
56
54
  pick_number: int | None
57
- repeat_number: int | None
55
+ weaving_repeat_number: int | None
58
56
 
59
57
 
60
58
  @dataclasses.dataclass
@@ -50,7 +50,7 @@
50
50
  <label>{of}</label>
51
51
  <label id="total_picks">?</label>
52
52
  <label>{repeat}</label>
53
- <label id="repeat_number"></label>
53
+ <label id="weaving_repeat_number"></label>
54
54
  </div>
55
55
 
56
56
  <form action="" id="jump_to_pick_form">
@@ -66,7 +66,7 @@ class ReducedPattern {
66
66
  this.threading = datadict.threading
67
67
  this.picks = []
68
68
  this.pick_number = datadict.pick_number
69
- this.repeat_number = datadict.repeat_number
69
+ this.weaving_repeat_number = datadict.weaving_repeat_number
70
70
  datadict.picks.forEach((pickdata) => {
71
71
  this.picks.push(new Pick(pickdata))
72
72
  })
@@ -209,12 +209,12 @@ class LoomClient {
209
209
  console.log("Ignoring CurrentPickNumber: no pattern loaded")
210
210
  }
211
211
  this.currentPattern.pick_number = datadict.pick_number
212
- this.currentPattern.repeat_number = datadict.repeat_number
212
+ this.currentPattern.weaving_repeat_number = datadict.weaving_repeat_number
213
213
  this.displayCurrentPattern()
214
214
  this.displayPick()
215
215
  } else if (datadict.type == "JumpPickNumber") {
216
216
  this.jumpPickNumber = datadict.pick_number
217
- this.jumpRepeatNumber = datadict.repeat_number
217
+ this.jumpRepeatNumber = datadict.weaving_repeat_number
218
218
  this.displayJumpPick()
219
219
  } else if (datadict.type == "LoomConnectionState") {
220
220
  this.loomConnectionState = datadict
@@ -505,7 +505,7 @@ class LoomClient {
505
505
  Display the current pick and repeat.
506
506
  */
507
507
  displayPick() {
508
- var repeatNumberElt = document.getElementById("repeat_number")
508
+ var repeatNumberElt = document.getElementById("weaving_repeat_number")
509
509
  var pickNumberElt = document.getElementById("pick_number")
510
510
  var totalPicksElt = document.getElementById("total_picks")
511
511
  var pickNumber = ""
@@ -513,7 +513,7 @@ class LoomClient {
513
513
  var repeatNumber = ""
514
514
  if (this.currentPattern) {
515
515
  pickNumber = this.currentPattern.pick_number
516
- repeatNumber = this.currentPattern.repeat_number
516
+ repeatNumber = this.currentPattern.weaving_repeat_number
517
517
  totalPicks = this.currentPattern.picks.length
518
518
  }
519
519
  pickNumberElt.textContent = pickNumber
@@ -644,7 +644,7 @@ class LoomClient {
644
644
  // Handle blanks by using the current default, if any
645
645
  var pickNumber = asNumberOrNull(jumpPickNumberElt.value)
646
646
  var repeatNumber = asNumberOrNull(jumpRepeatNumberElt.value)
647
- var command = { "type": "jump_to_pick", "pick_number": pickNumber, "repeat_number": repeatNumber }
647
+ var command = { "type": "jump_to_pick", "pick_number": pickNumber, "weaving_repeat_number": repeatNumber }
648
648
  await this.sendCommand(command)
649
649
  event.preventDefault()
650
650
  }
@@ -659,7 +659,7 @@ class LoomClient {
659
659
  var jumpRepeatNumberElt = document.getElementById("jump_repeat_number")
660
660
  jumpPickNumberElt.value = ""
661
661
  jumpRepeatNumberElt.value = ""
662
- var command = { "type": "jump_to_pick", "pick_number": null, "repeat_number": null }
662
+ var command = { "type": "jump_to_pick", "pick_number": null, "weaving_repeat_number": null }
663
663
  await this.sendCommand(command)
664
664
  event.preventDefault()
665
665
  }
@@ -1,6 +1,4 @@
1
- from __future__ import annotations
2
-
3
- __all__ = ["BaseLoomServer"]
1
+ __all__ = ["ExampleLoomServer"]
4
2
 
5
3
  import pathlib
6
4
 
@@ -10,10 +8,6 @@ from .example_mock_loom import ExampleMockLoom
10
8
  from .reduced_pattern import Pick
11
9
 
12
10
 
13
- class CommandError(Exception):
14
- pass
15
-
16
-
17
11
  class ExampleLoomServer(BaseLoomServer):
18
12
  """Example loom server.
19
13
 
@@ -1,5 +1,3 @@
1
- from __future__ import annotations
2
-
3
1
  __all__ = ["BaseMockLoom"]
4
2
 
5
3
  from .base_mock_loom import BaseMockLoom