log-ctrl 0.0.2__tar.gz → 0.0.4__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.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: log-ctrl
3
- Version: 0.0.2
3
+ Version: 0.0.4
4
4
  Summary: gRPC server and proxy for reading x_logger rotating log files by device class.
5
5
  Author-email: Kengo NAKADA <kengo.nakada@email.com>
6
6
  License: Apache License
@@ -230,16 +230,15 @@ Dynamic: license-file
230
230
 
231
231
  # log_ctrl
232
232
 
233
- [![en](https://img.shields.io/badge/lang-en-red.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.en.md)
234
- [![ja](https://img.shields.io/badge/lang-ja-yellow.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.md)
233
+ [![en](https://img.shields.io/badge/lang-en-red.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.md)
234
+ [![ja](https://img.shields.io/badge/lang-ja-yellow.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.ja.md)
235
235
 
236
- `log_ctrl`
237
- は、指定したログディレクトリに保存されているログファイルを、`grpc_frame`
238
- を使ってネットワーク越しに参照するためのパッケージです。
236
+ `log_ctrl` is a package for accessing log files stored in a specified
237
+ log directory over a network using `grpc_frame`.
239
238
 
240
- ログを書き込む側の DeviceServer やアプリケーションにはログ取得 RPC
241
- を追加しません。`log_ctrl` は既存のログファイルを read-only
242
- で参照する独立した gRPC サーバーとして動作します。
239
+ It does not add log retrieval RPCs to the DeviceServer or application
240
+ that writes the logs. `log_ctrl` runs as an independent, read-only gRPC
241
+ server that accesses existing log files.
243
242
 
244
243
  ``` text
245
244
  application / DeviceServer
@@ -263,9 +262,9 @@ C:\opt\ese774\log
263
262
  DeviceProxy("log", ...)
264
263
  ```
265
264
 
266
- ## ログ名
265
+ ## Log names
267
266
 
268
- `log_ctrl` では、`.log` より前の部分を `log_name` と呼びます。
267
+ In `log_ctrl`, the part before `.log` is called the `log_name`.
269
268
 
270
269
  ``` text
271
270
  cobotta4_server.log
@@ -273,47 +272,52 @@ cobotta4_server.log
273
272
  log_name
274
273
  ```
275
274
 
276
- ローテーション済みログは次の形式です。
275
+ Rotated log files use the following format:
277
276
 
278
277
  ``` text
279
278
  <log_name>.log.YYYY-MM-DD
280
279
  ```
281
280
 
282
- `log_name` は DeviceServer
283
- 名やデバイスクラス名と一致する必要はありません。`log_ctrl`
284
- はファイル名として存在する `log_name` をそのまま扱います。
281
+ The `log_name` does not need to match the DeviceServer name or device
282
+ class name. `log_ctrl` uses the `log_name` exactly as it appears in the
283
+ filename.
285
284
 
286
- ## 主な機能
285
+ ## Main features
287
286
 
288
- - `log_names()` : 実在するログファイルから `log_name` 一覧を取得
289
- - `dates(log_name)` : 指定した `log_name`
290
- のローテーション日付一覧を取得
291
- - `exists(log_name, date=None)` : 現在ログまたは指定日ログの存在確認
292
- - `tail(log_name, lines=100, date=None)` : ログ末尾を文字列で取得
293
- - `raw_files()` : ログディレクトリ以下の全ファイルを相対パスで列挙
294
- - `read(log_name, date=None)` : ログファイル本体を `bytes` で取得
295
- - `read_raw(relative_path)` : `raw_files()` で確認した任意ファイルを
296
- `bytes` で取得
287
+ - `log_names()`: Get the list of `log_name` values from existing log
288
+ files.
289
+ - `dates(log_name)`: Get the list of rotation dates for the specified
290
+ `log_name`.
291
+ - `exists(log_name, date=None)`: Check whether the current log or a
292
+ log for a specified date exists.
293
+ - `tail(log_name, lines=100, date=None)`: Get the end of a log as a
294
+ string.
295
+ - `raw_files()`: List all files under the log directory as relative
296
+ paths.
297
+ - `read(log_name, date=None)`: Read a log file as `bytes`.
298
+ - `read_raw(relative_path)`: Read an arbitrary file confirmed by
299
+ `raw_files()` as `bytes`.
297
300
 
298
- 大きなログファイルは `grpc_frame` の `StreamCall`
299
- を使ってチャンク転送します。利用側ではストリーム処理を直接扱う必要はなく、`read()`
300
- / `read_raw()` が受信したチャンクを結合して `bytes` として返します。
301
+ Large log files are transferred in chunks using `grpc_frame`
302
+ `StreamCall`. Client-side code does not need to handle the stream
303
+ directly; `read()` and `read_raw()` join the received chunks and return
304
+ them as `bytes`.
301
305
 
302
- ## インストール
306
+ ## Installation
303
307
 
304
- `grpc_frame` を利用可能な環境でインストールします。
308
+ Install in an environment where `grpc_frame` is available.
305
309
 
306
310
  ``` bash
307
311
  python -m pip install .
308
312
  ```
309
313
 
310
- 開発時は次のように editable install できます。
314
+ For development, use an editable install:
311
315
 
312
316
  ``` bash
313
317
  python -m pip install -e .
314
318
  ```
315
319
 
316
- ## LogServer の起動
320
+ ## Starting LogServer
317
321
 
318
322
  ``` python
319
323
  from log_ctrl.server_grpc import log_grpc_server
@@ -329,12 +333,12 @@ log_grpc_server(
329
333
  )
330
334
  ```
331
335
 
332
- `logger` を省略した場合は標準の `logging` が使用されます。既存の logger
333
- を使用する場合は `logger=` で渡せます。
336
+ If `logger` is omitted, the standard `logging` module is used. To use an
337
+ existing logger, pass it with `logger=`.
334
338
 
335
- ## クライアント
339
+ ## Client
336
340
 
337
- `grpc_frame` の透過クライアントとして `DeviceProxy` を使用します。
341
+ Use `DeviceProxy` as the transparent `grpc_frame` client.
338
342
 
339
343
  ``` python
340
344
  from log_ctrl.server_grpc import DeviceProxy
@@ -364,9 +368,10 @@ finally:
364
368
  client.close()
365
369
  ```
366
370
 
367
- `log_names()` で返される名前は、現在の `<log_name>.log`
368
- が存在する名前だけとは限りません。ローテーション済みファイルだけが残っている場合も一覧に含まれます。現在ログを読む前に必要に応じて
369
- `exists(log_name)` を確認してください。
371
+ The names returned by `log_names()` are not limited to names for which a
372
+ current `<log_name>.log` file exists. A name is also included when only
373
+ rotated log files remain. Check `exists(log_name)` as needed before
374
+ reading the current log.
370
375
 
371
376
  ## API
372
377
 
@@ -388,20 +393,19 @@ client.read(log_name, date="2026-04-06")
388
393
  client.read_raw("cobotta4_server.log.2026-04-06")
389
394
  ```
390
395
 
391
- `read()` と `read_raw()` の戻り値は `bytes`
392
- です。ログを文字列として扱う場合は、使用している文字コードに合わせてクライアント側で
393
- decode します。
396
+ `read()` and `read_raw()` return `bytes`. To handle a log as text,
397
+ decode it on the client using the appropriate character encoding.
394
398
 
395
399
  ``` python
396
400
  text = client.read(log_name).decode("utf-8")
397
401
  ```
398
402
 
399
- `tail()` はサーバー側で設定された `encoding` を使って decode され、`str`
400
- を返します。
403
+ `tail()` is decoded on the server using the configured `encoding` and
404
+ returns `str`.
401
405
 
402
- ## ドキュメント
406
+ ## Documentation
403
407
 
404
- Sphinx 用文書は `docs/` にあります。
408
+ Sphinx documentation is available under `docs/`.
405
409
 
406
410
  - `docs/index.md`
407
411
  - `docs/quickstart.md`
@@ -411,4 +415,4 @@ Sphinx 用文書は `docs/` にあります。
411
415
 
412
416
  ## License
413
417
 
414
- `LICENSE` を参照してください。
418
+ See `LICENSE`.
@@ -0,0 +1,188 @@
1
+ # log_ctrl
2
+
3
+ [![en](https://img.shields.io/badge/lang-en-red.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.md)
4
+ [![ja](https://img.shields.io/badge/lang-ja-yellow.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.ja.md)
5
+
6
+ `log_ctrl` is a package for accessing log files stored in a specified
7
+ log directory over a network using `grpc_frame`.
8
+
9
+ It does not add log retrieval RPCs to the DeviceServer or application
10
+ that writes the logs. `log_ctrl` runs as an independent, read-only gRPC
11
+ server that accesses existing log files.
12
+
13
+ ``` text
14
+ application / DeviceServer
15
+ │
16
+ │ write
17
+ ▼
18
+ C:\opt\ese774\log
19
+ ├── cobotta4_server.log
20
+ ├── cobotta4_server.log.2026-04-06
21
+ ├── cobotta4_server2.log
22
+ └── cobotta4_server2.log.2026-06-16
23
+ ▲
24
+ │ read only
25
+ │
26
+ LogCtrl
27
+ │
28
+ ▼
29
+ log gRPC server
30
+ │
31
+ ▼
32
+ DeviceProxy("log", ...)
33
+ ```
34
+
35
+ ## Log names
36
+
37
+ In `log_ctrl`, the part before `.log` is called the `log_name`.
38
+
39
+ ``` text
40
+ cobotta4_server.log
41
+ ^^^^^^^^^^^^^^^
42
+ log_name
43
+ ```
44
+
45
+ Rotated log files use the following format:
46
+
47
+ ``` text
48
+ <log_name>.log.YYYY-MM-DD
49
+ ```
50
+
51
+ The `log_name` does not need to match the DeviceServer name or device
52
+ class name. `log_ctrl` uses the `log_name` exactly as it appears in the
53
+ filename.
54
+
55
+ ## Main features
56
+
57
+ - `log_names()`: Get the list of `log_name` values from existing log
58
+ files.
59
+ - `dates(log_name)`: Get the list of rotation dates for the specified
60
+ `log_name`.
61
+ - `exists(log_name, date=None)`: Check whether the current log or a
62
+ log for a specified date exists.
63
+ - `tail(log_name, lines=100, date=None)`: Get the end of a log as a
64
+ string.
65
+ - `raw_files()`: List all files under the log directory as relative
66
+ paths.
67
+ - `read(log_name, date=None)`: Read a log file as `bytes`.
68
+ - `read_raw(relative_path)`: Read an arbitrary file confirmed by
69
+ `raw_files()` as `bytes`.
70
+
71
+ Large log files are transferred in chunks using `grpc_frame`
72
+ `StreamCall`. Client-side code does not need to handle the stream
73
+ directly; `read()` and `read_raw()` join the received chunks and return
74
+ them as `bytes`.
75
+
76
+ ## Installation
77
+
78
+ Install in an environment where `grpc_frame` is available.
79
+
80
+ ``` bash
81
+ python -m pip install .
82
+ ```
83
+
84
+ For development, use an editable install:
85
+
86
+ ``` bash
87
+ python -m pip install -e .
88
+ ```
89
+
90
+ ## Starting LogServer
91
+
92
+ ``` python
93
+ from log_ctrl.server_grpc import log_grpc_server
94
+
95
+ GRPC_HOST = "0.0.0.0"
96
+ GRPC_PORT = 50060
97
+ LOG_DIR = r"C:\opt\ese774\log"
98
+
99
+ log_grpc_server(
100
+ grpc_host=GRPC_HOST,
101
+ grpc_port=GRPC_PORT,
102
+ log_dir=LOG_DIR,
103
+ )
104
+ ```
105
+
106
+ If `logger` is omitted, the standard `logging` module is used. To use an
107
+ existing logger, pass it with `logger=`.
108
+
109
+ ## Client
110
+
111
+ Use `DeviceProxy` as the transparent `grpc_frame` client.
112
+
113
+ ``` python
114
+ from log_ctrl.server_grpc import DeviceProxy
115
+
116
+ client = DeviceProxy(
117
+ "log",
118
+ server_ip="127.0.0.1",
119
+ server_port=50060,
120
+ set_timeout_sec=10.0,
121
+ async_mode=False,
122
+ )
123
+
124
+ try:
125
+ log_names = client.log_names()
126
+ print(log_names)
127
+
128
+ if len(log_names) > 0:
129
+ log_name = log_names[0]
130
+
131
+ print(client.dates(log_name))
132
+
133
+ if client.exists(log_name):
134
+ data = client.read(log_name)
135
+ print(len(data))
136
+
137
+ finally:
138
+ client.close()
139
+ ```
140
+
141
+ The names returned by `log_names()` are not limited to names for which a
142
+ current `<log_name>.log` file exists. A name is also included when only
143
+ rotated log files remain. Check `exists(log_name)` as needed before
144
+ reading the current log.
145
+
146
+ ## API
147
+
148
+ ``` python
149
+ client.log_names()
150
+ client.dates(log_name)
151
+
152
+ client.exists(log_name)
153
+ client.exists(log_name, date="2026-04-06")
154
+
155
+ client.tail(log_name, lines=100)
156
+ client.tail(log_name, lines=100, date="2026-04-06")
157
+
158
+ client.raw_files()
159
+
160
+ client.read(log_name)
161
+ client.read(log_name, date="2026-04-06")
162
+
163
+ client.read_raw("cobotta4_server.log.2026-04-06")
164
+ ```
165
+
166
+ `read()` and `read_raw()` return `bytes`. To handle a log as text,
167
+ decode it on the client using the appropriate character encoding.
168
+
169
+ ``` python
170
+ text = client.read(log_name).decode("utf-8")
171
+ ```
172
+
173
+ `tail()` is decoded on the server using the configured `encoding` and
174
+ returns `str`.
175
+
176
+ ## Documentation
177
+
178
+ Sphinx documentation is available under `docs/`.
179
+
180
+ - `docs/index.md`
181
+ - `docs/quickstart.md`
182
+ - `docs/usage.md`
183
+ - `docs/rotation.md`
184
+ - `docs/architecture.md`
185
+
186
+ ## License
187
+
188
+ See `LICENSE`.
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "log-ctrl"
7
- version = "0.0.2"
7
+ version = "0.0.4"
8
8
 
9
9
  description = "gRPC server and proxy for reading x_logger rotating log files by device class."
10
10
  readme = "README.md"
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: log-ctrl
3
- Version: 0.0.2
3
+ Version: 0.0.4
4
4
  Summary: gRPC server and proxy for reading x_logger rotating log files by device class.
5
5
  Author-email: Kengo NAKADA <kengo.nakada@email.com>
6
6
  License: Apache License
@@ -230,16 +230,15 @@ Dynamic: license-file
230
230
 
231
231
  # log_ctrl
232
232
 
233
- [![en](https://img.shields.io/badge/lang-en-red.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.en.md)
234
- [![ja](https://img.shields.io/badge/lang-ja-yellow.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.md)
233
+ [![en](https://img.shields.io/badge/lang-en-red.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.md)
234
+ [![ja](https://img.shields.io/badge/lang-ja-yellow.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.ja.md)
235
235
 
236
- `log_ctrl`
237
- は、指定したログディレクトリに保存されているログファイルを、`grpc_frame`
238
- を使ってネットワーク越しに参照するためのパッケージです。
236
+ `log_ctrl` is a package for accessing log files stored in a specified
237
+ log directory over a network using `grpc_frame`.
239
238
 
240
- ログを書き込む側の DeviceServer やアプリケーションにはログ取得 RPC
241
- を追加しません。`log_ctrl` は既存のログファイルを read-only
242
- で参照する独立した gRPC サーバーとして動作します。
239
+ It does not add log retrieval RPCs to the DeviceServer or application
240
+ that writes the logs. `log_ctrl` runs as an independent, read-only gRPC
241
+ server that accesses existing log files.
243
242
 
244
243
  ``` text
245
244
  application / DeviceServer
@@ -263,9 +262,9 @@ C:\opt\ese774\log
263
262
  DeviceProxy("log", ...)
264
263
  ```
265
264
 
266
- ## ログ名
265
+ ## Log names
267
266
 
268
- `log_ctrl` では、`.log` より前の部分を `log_name` と呼びます。
267
+ In `log_ctrl`, the part before `.log` is called the `log_name`.
269
268
 
270
269
  ``` text
271
270
  cobotta4_server.log
@@ -273,47 +272,52 @@ cobotta4_server.log
273
272
  log_name
274
273
  ```
275
274
 
276
- ローテーション済みログは次の形式です。
275
+ Rotated log files use the following format:
277
276
 
278
277
  ``` text
279
278
  <log_name>.log.YYYY-MM-DD
280
279
  ```
281
280
 
282
- `log_name` は DeviceServer
283
- 名やデバイスクラス名と一致する必要はありません。`log_ctrl`
284
- はファイル名として存在する `log_name` をそのまま扱います。
281
+ The `log_name` does not need to match the DeviceServer name or device
282
+ class name. `log_ctrl` uses the `log_name` exactly as it appears in the
283
+ filename.
285
284
 
286
- ## 主な機能
285
+ ## Main features
287
286
 
288
- - `log_names()` : 実在するログファイルから `log_name` 一覧を取得
289
- - `dates(log_name)` : 指定した `log_name`
290
- のローテーション日付一覧を取得
291
- - `exists(log_name, date=None)` : 現在ログまたは指定日ログの存在確認
292
- - `tail(log_name, lines=100, date=None)` : ログ末尾を文字列で取得
293
- - `raw_files()` : ログディレクトリ以下の全ファイルを相対パスで列挙
294
- - `read(log_name, date=None)` : ログファイル本体を `bytes` で取得
295
- - `read_raw(relative_path)` : `raw_files()` で確認した任意ファイルを
296
- `bytes` で取得
287
+ - `log_names()`: Get the list of `log_name` values from existing log
288
+ files.
289
+ - `dates(log_name)`: Get the list of rotation dates for the specified
290
+ `log_name`.
291
+ - `exists(log_name, date=None)`: Check whether the current log or a
292
+ log for a specified date exists.
293
+ - `tail(log_name, lines=100, date=None)`: Get the end of a log as a
294
+ string.
295
+ - `raw_files()`: List all files under the log directory as relative
296
+ paths.
297
+ - `read(log_name, date=None)`: Read a log file as `bytes`.
298
+ - `read_raw(relative_path)`: Read an arbitrary file confirmed by
299
+ `raw_files()` as `bytes`.
297
300
 
298
- 大きなログファイルは `grpc_frame` の `StreamCall`
299
- を使ってチャンク転送します。利用側ではストリーム処理を直接扱う必要はなく、`read()`
300
- / `read_raw()` が受信したチャンクを結合して `bytes` として返します。
301
+ Large log files are transferred in chunks using `grpc_frame`
302
+ `StreamCall`. Client-side code does not need to handle the stream
303
+ directly; `read()` and `read_raw()` join the received chunks and return
304
+ them as `bytes`.
301
305
 
302
- ## インストール
306
+ ## Installation
303
307
 
304
- `grpc_frame` を利用可能な環境でインストールします。
308
+ Install in an environment where `grpc_frame` is available.
305
309
 
306
310
  ``` bash
307
311
  python -m pip install .
308
312
  ```
309
313
 
310
- 開発時は次のように editable install できます。
314
+ For development, use an editable install:
311
315
 
312
316
  ``` bash
313
317
  python -m pip install -e .
314
318
  ```
315
319
 
316
- ## LogServer の起動
320
+ ## Starting LogServer
317
321
 
318
322
  ``` python
319
323
  from log_ctrl.server_grpc import log_grpc_server
@@ -329,12 +333,12 @@ log_grpc_server(
329
333
  )
330
334
  ```
331
335
 
332
- `logger` を省略した場合は標準の `logging` が使用されます。既存の logger
333
- を使用する場合は `logger=` で渡せます。
336
+ If `logger` is omitted, the standard `logging` module is used. To use an
337
+ existing logger, pass it with `logger=`.
334
338
 
335
- ## クライアント
339
+ ## Client
336
340
 
337
- `grpc_frame` の透過クライアントとして `DeviceProxy` を使用します。
341
+ Use `DeviceProxy` as the transparent `grpc_frame` client.
338
342
 
339
343
  ``` python
340
344
  from log_ctrl.server_grpc import DeviceProxy
@@ -364,9 +368,10 @@ finally:
364
368
  client.close()
365
369
  ```
366
370
 
367
- `log_names()` で返される名前は、現在の `<log_name>.log`
368
- が存在する名前だけとは限りません。ローテーション済みファイルだけが残っている場合も一覧に含まれます。現在ログを読む前に必要に応じて
369
- `exists(log_name)` を確認してください。
371
+ The names returned by `log_names()` are not limited to names for which a
372
+ current `<log_name>.log` file exists. A name is also included when only
373
+ rotated log files remain. Check `exists(log_name)` as needed before
374
+ reading the current log.
370
375
 
371
376
  ## API
372
377
 
@@ -388,20 +393,19 @@ client.read(log_name, date="2026-04-06")
388
393
  client.read_raw("cobotta4_server.log.2026-04-06")
389
394
  ```
390
395
 
391
- `read()` と `read_raw()` の戻り値は `bytes`
392
- です。ログを文字列として扱う場合は、使用している文字コードに合わせてクライアント側で
393
- decode します。
396
+ `read()` and `read_raw()` return `bytes`. To handle a log as text,
397
+ decode it on the client using the appropriate character encoding.
394
398
 
395
399
  ``` python
396
400
  text = client.read(log_name).decode("utf-8")
397
401
  ```
398
402
 
399
- `tail()` はサーバー側で設定された `encoding` を使って decode され、`str`
400
- を返します。
403
+ `tail()` is decoded on the server using the configured `encoding` and
404
+ returns `str`.
401
405
 
402
- ## ドキュメント
406
+ ## Documentation
403
407
 
404
- Sphinx 用文書は `docs/` にあります。
408
+ Sphinx documentation is available under `docs/`.
405
409
 
406
410
  - `docs/index.md`
407
411
  - `docs/quickstart.md`
@@ -411,4 +415,4 @@ Sphinx 用文書は `docs/` にあります。
411
415
 
412
416
  ## License
413
417
 
414
- `LICENSE` を参照してください。
418
+ See `LICENSE`.
log_ctrl-0.0.2/README.md DELETED
@@ -1,184 +0,0 @@
1
- # log_ctrl
2
-
3
- [![en](https://img.shields.io/badge/lang-en-red.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.en.md)
4
- [![ja](https://img.shields.io/badge/lang-ja-yellow.svg)](https://github.com/ohara-lab-su/log_ctrl/blob/main/README.md)
5
-
6
- `log_ctrl`
7
- は、指定したログディレクトリに保存されているログファイルを、`grpc_frame`
8
- を使ってネットワーク越しに参照するためのパッケージです。
9
-
10
- ログを書き込む側の DeviceServer やアプリケーションにはログ取得 RPC
11
- を追加しません。`log_ctrl` は既存のログファイルを read-only
12
- で参照する独立した gRPC サーバーとして動作します。
13
-
14
- ``` text
15
- application / DeviceServer
16
- │
17
- │ write
18
- ▼
19
- C:\opt\ese774\log
20
- ├── cobotta4_server.log
21
- ├── cobotta4_server.log.2026-04-06
22
- ├── cobotta4_server2.log
23
- └── cobotta4_server2.log.2026-06-16
24
- ▲
25
- │ read only
26
- │
27
- LogCtrl
28
- │
29
- ▼
30
- log gRPC server
31
- │
32
- ▼
33
- DeviceProxy("log", ...)
34
- ```
35
-
36
- ## ログ名
37
-
38
- `log_ctrl` では、`.log` より前の部分を `log_name` と呼びます。
39
-
40
- ``` text
41
- cobotta4_server.log
42
- ^^^^^^^^^^^^^^^
43
- log_name
44
- ```
45
-
46
- ローテーション済みログは次の形式です。
47
-
48
- ``` text
49
- <log_name>.log.YYYY-MM-DD
50
- ```
51
-
52
- `log_name` は DeviceServer
53
- 名やデバイスクラス名と一致する必要はありません。`log_ctrl`
54
- はファイル名として存在する `log_name` をそのまま扱います。
55
-
56
- ## 主な機能
57
-
58
- - `log_names()` : 実在するログファイルから `log_name` 一覧を取得
59
- - `dates(log_name)` : 指定した `log_name`
60
- のローテーション日付一覧を取得
61
- - `exists(log_name, date=None)` : 現在ログまたは指定日ログの存在確認
62
- - `tail(log_name, lines=100, date=None)` : ログ末尾を文字列で取得
63
- - `raw_files()` : ログディレクトリ以下の全ファイルを相対パスで列挙
64
- - `read(log_name, date=None)` : ログファイル本体を `bytes` で取得
65
- - `read_raw(relative_path)` : `raw_files()` で確認した任意ファイルを
66
- `bytes` で取得
67
-
68
- 大きなログファイルは `grpc_frame` の `StreamCall`
69
- を使ってチャンク転送します。利用側ではストリーム処理を直接扱う必要はなく、`read()`
70
- / `read_raw()` が受信したチャンクを結合して `bytes` として返します。
71
-
72
- ## インストール
73
-
74
- `grpc_frame` を利用可能な環境でインストールします。
75
-
76
- ``` bash
77
- python -m pip install .
78
- ```
79
-
80
- 開発時は次のように editable install できます。
81
-
82
- ``` bash
83
- python -m pip install -e .
84
- ```
85
-
86
- ## LogServer の起動
87
-
88
- ``` python
89
- from log_ctrl.server_grpc import log_grpc_server
90
-
91
- GRPC_HOST = "0.0.0.0"
92
- GRPC_PORT = 50060
93
- LOG_DIR = r"C:\opt\ese774\log"
94
-
95
- log_grpc_server(
96
- grpc_host=GRPC_HOST,
97
- grpc_port=GRPC_PORT,
98
- log_dir=LOG_DIR,
99
- )
100
- ```
101
-
102
- `logger` を省略した場合は標準の `logging` が使用されます。既存の logger
103
- を使用する場合は `logger=` で渡せます。
104
-
105
- ## クライアント
106
-
107
- `grpc_frame` の透過クライアントとして `DeviceProxy` を使用します。
108
-
109
- ``` python
110
- from log_ctrl.server_grpc import DeviceProxy
111
-
112
- client = DeviceProxy(
113
- "log",
114
- server_ip="127.0.0.1",
115
- server_port=50060,
116
- set_timeout_sec=10.0,
117
- async_mode=False,
118
- )
119
-
120
- try:
121
- log_names = client.log_names()
122
- print(log_names)
123
-
124
- if len(log_names) > 0:
125
- log_name = log_names[0]
126
-
127
- print(client.dates(log_name))
128
-
129
- if client.exists(log_name):
130
- data = client.read(log_name)
131
- print(len(data))
132
-
133
- finally:
134
- client.close()
135
- ```
136
-
137
- `log_names()` で返される名前は、現在の `<log_name>.log`
138
- が存在する名前だけとは限りません。ローテーション済みファイルだけが残っている場合も一覧に含まれます。現在ログを読む前に必要に応じて
139
- `exists(log_name)` を確認してください。
140
-
141
- ## API
142
-
143
- ``` python
144
- client.log_names()
145
- client.dates(log_name)
146
-
147
- client.exists(log_name)
148
- client.exists(log_name, date="2026-04-06")
149
-
150
- client.tail(log_name, lines=100)
151
- client.tail(log_name, lines=100, date="2026-04-06")
152
-
153
- client.raw_files()
154
-
155
- client.read(log_name)
156
- client.read(log_name, date="2026-04-06")
157
-
158
- client.read_raw("cobotta4_server.log.2026-04-06")
159
- ```
160
-
161
- `read()` と `read_raw()` の戻り値は `bytes`
162
- です。ログを文字列として扱う場合は、使用している文字コードに合わせてクライアント側で
163
- decode します。
164
-
165
- ``` python
166
- text = client.read(log_name).decode("utf-8")
167
- ```
168
-
169
- `tail()` はサーバー側で設定された `encoding` を使って decode され、`str`
170
- を返します。
171
-
172
- ## ドキュメント
173
-
174
- Sphinx 用文書は `docs/` にあります。
175
-
176
- - `docs/index.md`
177
- - `docs/quickstart.md`
178
- - `docs/usage.md`
179
- - `docs/rotation.md`
180
- - `docs/architecture.md`
181
-
182
- ## License
183
-
184
- `LICENSE` を参照してください。
File without changes
File without changes