├── .gitignore
├── .pyrustic
└── buildver
│ └── build_report
├── LICENSE
├── MANIFEST.in
├── README.md
├── VERSION
├── docs
└── api
│ ├── MIKEDOC
│ ├── README.md
│ └── modules
│ └── jinbase
│ ├── __init__
│ ├── README.md
│ ├── class-Jinbase.md
│ ├── class-Model.md
│ ├── class-RecordInfo.md
│ ├── class-TimestampPrecision.md
│ ├── class-TypeRef.md
│ └── fields.md
│ ├── blob
│ └── __init__
│ │ ├── README.md
│ │ └── class-Blob.md
│ ├── const
│ └── __init__
│ │ ├── README.md
│ │ ├── class-Model.md
│ │ ├── class-StorageUnit.md
│ │ ├── class-TimeUnit.md
│ │ ├── class-TimestampPrecision.md
│ │ └── fields.md
│ └── store
│ ├── __init__
│ ├── README.md
│ ├── class-RecordInfo.md
│ └── class-Store.md
│ ├── depot
│ ├── README.md
│ └── class-Depot.md
│ ├── kv
│ ├── README.md
│ └── class-Kv.md
│ ├── queue
│ ├── README.md
│ └── class-Queue.md
│ └── stack
│ ├── README.md
│ └── class-Stack.md
├── mikedoc.kvf
├── pyproject.toml
├── setup.cfg
├── setup.py
├── src
└── jinbase
│ ├── __init__.py
│ ├── __main__.py
│ ├── blob
│ └── __init__.py
│ ├── const
│ └── __init__.py
│ ├── errors
│ └── __init__.py
│ ├── misc
│ └── __init__.py
│ ├── queries
│ └── __init__.py
│ ├── store
│ ├── __init__.py
│ ├── depot.py
│ ├── kv.py
│ ├── queue.py
│ └── stack.py
│ └── transaction_policy.txt
└── tests
├── __init__.py
├── __main__.py
├── test_blob.py
├── test_depot.py
├── test_imports.py
├── test_jinbase.py
├── test_kv.py
├── test_misc.py
├── test_queue.py
└── test_stack.py
/.gitignore:
--------------------------------------------------------------------------------
1 | # Python
2 | __pycache__/
3 | *.py[cod]
4 | build/
5 | dist/
6 | *.egg-info/
7 |
8 | # Environments
9 | venv/
10 | env/
11 |
12 | # PyCharm
13 | .idea/
14 |
15 |
--------------------------------------------------------------------------------
/.pyrustic/buildver/build_report:
--------------------------------------------------------------------------------
1 | 0.0.5 1733864063
2 | 0.0.4 1733863804
3 | 0.0.3 1732907360
4 | 0.0.2 1732573634
5 |
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | MIT License
2 |
3 | Copyright (c) 2023, 2024 Pyrustic Architect
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
--------------------------------------------------------------------------------
/MANIFEST.in:
--------------------------------------------------------------------------------
1 | include VERSION
2 | recursive-include src *
3 | global-exclude *.py[cod]
4 |
--------------------------------------------------------------------------------
/VERSION:
--------------------------------------------------------------------------------
1 | 0.0.6
--------------------------------------------------------------------------------
/docs/api/MIKEDOC:
--------------------------------------------------------------------------------
1 | API Reference generated with [MikeDoc](https://github.com/pyrustic/mikedoc).
2 |
--------------------------------------------------------------------------------
/docs/api/README.md:
--------------------------------------------------------------------------------
1 | # Jinbase API Reference
2 | Here are modules that make up [Jinbase](/README.md):
3 |
4 | [jinbase.\_\_init\_\_](/docs/api/modules/jinbase/__init__/README.md)
5 |
6 | The main module of Jinbase.
7 |
8 | [jinbase.blob.\_\_init\_\_](/docs/api/modules/jinbase/blob/__init__/README.md)
9 |
10 | The Blob class is defined here.
11 |
12 | [jinbase.const.\_\_init\_\_](/docs/api/modules/jinbase/const/__init__/README.md)
13 |
14 | Project-wide constants are defined in this module.
15 |
16 | [jinbase.store.\_\_init\_\_](/docs/api/modules/jinbase/store/__init__/README.md)
17 |
18 | The abstract Store class is defined in this module.
19 |
20 | [jinbase.store.depot](/docs/api/modules/jinbase/store/depot/README.md)
21 |
22 | The Depot store is defined in this module.
23 |
24 | [jinbase.store.kv](/docs/api/modules/jinbase/store/kv/README.md)
25 |
26 | The Kv store is defined in this module.
27 |
28 | [jinbase.store.queue](/docs/api/modules/jinbase/store/queue/README.md)
29 |
30 | The Queue store is defined in this module.
31 |
32 | [jinbase.store.stack](/docs/api/modules/jinbase/store/stack/README.md)
33 |
34 | The Stack store is defined in this module.
35 |
36 |
Back to top
37 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/__init__/README.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | Module | [Source](/src/jinbase/__init__.py)
3 |
4 | # Module Overview
5 | > Module: **jinbase.\_\_init\_\_**
6 |
7 | The main module of Jinbase.
8 |
9 | ## Fields
10 | - [**All fields**](/docs/api/modules/jinbase/__init__/fields.md)
11 | - CHUNK\_SIZE = `1048576`
12 | - DATETIME\_FORMAT = `'%Y-%m-%d %H:%M:%S.%fZ'`
13 | - JINBASE\_HOME = `'/home/alex/JinbaseHome'`
14 | - JINBASE\_VERSION = `1`
15 | - TIMEOUT = `5.0`
16 | - TIMESTAMP\_PRECISION = ``
17 | - USER\_HOME = `'/home/alex'`
18 |
19 | Back to top
20 |
21 | ## Classes
22 | - [**Jinbase**](/docs/api/modules/jinbase/__init__/class-Jinbase.md): The Jinbase class. A Jinbase object is intended to be directly instantiated by the user.
23 | - [chunk\_size](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
24 | - [created\_at](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
25 | - [creation\_dt](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
26 | - [dbc](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
27 | - [depot](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
28 | - [filename](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
29 | - [in\_memory](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
30 | - [is\_closed](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
31 | - [is\_destroyed](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
32 | - [is\_new](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
33 | - [is\_readonly](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
34 | - [kv](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
35 | - [queue](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
36 | - [stack](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
37 | - [timeout](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
38 | - [timestamp\_precision](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
39 | - [type\_ref](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
40 | - [version](/docs/api/modules/jinbase/__init__/class-Jinbase.md#properties-table); _getter_
41 | - [backup](/docs/api/modules/jinbase/__init__/class-Jinbase.md#backup): No docstring.
42 | - [close](/docs/api/modules/jinbase/__init__/class-Jinbase.md#close): Close the connection
43 | - [copy](/docs/api/modules/jinbase/__init__/class-Jinbase.md#copy): Create a new Jinbase instance that points to the same database file
44 | - [count\_bytes](/docs/api/modules/jinbase/__init__/class-Jinbase.md#count_bytes): No docstring.
45 | - [count\_chunks](/docs/api/modules/jinbase/__init__/class-Jinbase.md#count_chunks): No docstring.
46 | - [count\_records](/docs/api/modules/jinbase/__init__/class-Jinbase.md#count_records): No docstring.
47 | - [destroy](/docs/api/modules/jinbase/__init__/class-Jinbase.md#destroy): Destroy the database file
48 | - [get\_journal\_mode](/docs/api/modules/jinbase/__init__/class-Jinbase.md#get_journal_mode): No docstring.
49 | - [get\_locking\_mode](/docs/api/modules/jinbase/__init__/class-Jinbase.md#get_locking_mode): No docstring.
50 | - [get\_sync\_mode](/docs/api/modules/jinbase/__init__/class-Jinbase.md#get_sync_mode): No docstring.
51 | - [interrupt](/docs/api/modules/jinbase/__init__/class-Jinbase.md#interrupt): No docstring.
52 | - [iterdump](/docs/api/modules/jinbase/__init__/class-Jinbase.md#iterdump): Returns an iterator to the dump of the database in an SQL text format
53 | - [latest](/docs/api/modules/jinbase/__init__/class-Jinbase.md#latest): Get the utc datetime of the latest operation.
54 | - [now](/docs/api/modules/jinbase/__init__/class-Jinbase.md#now): Get the current utc datetime.
55 | - [now\_dt](/docs/api/modules/jinbase/__init__/class-Jinbase.md#now_dt): Get the current utc datetime.
56 | - [read\_transaction](/docs/api/modules/jinbase/__init__/class-Jinbase.md#read_transaction): No docstring.
57 | - [scan](/docs/api/modules/jinbase/__init__/class-Jinbase.md#scan): Scan the Jinbase database
58 | - [set\_journal\_mode](/docs/api/modules/jinbase/__init__/class-Jinbase.md#set_journal_mode): No docstring.
59 | - [set\_locking\_mode](/docs/api/modules/jinbase/__init__/class-Jinbase.md#set_locking_mode): No docstring.
60 | - [set\_progress\_handler](/docs/api/modules/jinbase/__init__/class-Jinbase.md#set_progress_handler): No docstring.
61 | - [set\_sync\_mode](/docs/api/modules/jinbase/__init__/class-Jinbase.md#set_sync_mode): No docstring.
62 | - [set\_trace\_callback](/docs/api/modules/jinbase/__init__/class-Jinbase.md#set_trace_callback): No docstring.
63 | - [transaction](/docs/api/modules/jinbase/__init__/class-Jinbase.md#transaction): No docstring.
64 | - [vacuum](/docs/api/modules/jinbase/__init__/class-Jinbase.md#vacuum): Vacuum the database
65 | - [vacuum\_into](/docs/api/modules/jinbase/__init__/class-Jinbase.md#vacuum_into): Vacuum into a file whose name is provided via `dst`.
66 | - [write\_transaction](/docs/api/modules/jinbase/__init__/class-Jinbase.md#write_transaction): No docstring.
67 | - [**Model**](/docs/api/modules/jinbase/__init__/class-Model.md): Create a collection of name/value pairs.
68 | - KV = `1`
69 | - DEPOT = `2`
70 | - QUEUE = `3`
71 | - STACK = `4`
72 | - [**RecordInfo**](/docs/api/modules/jinbase/__init__/class-RecordInfo.md): Named tuple returned by store.info()
73 | - uid: Alias for field number 0
74 | - datatype: Alias for field number 1
75 | - created\_at: Alias for field number 2
76 | - [**TimestampPrecision**](/docs/api/modules/jinbase/__init__/class-TimestampPrecision.md): Create a collection of name/value pairs.
77 | - SECONDS = `0`
78 | - MILLISECONDS = `3`
79 | - MICROSECONDS = `6`
80 | - NANOSECONDS = `9`
81 | - [**TypeRef**](/docs/api/modules/jinbase/__init__/class-TypeRef.md): This class represents a mechanism for customizing Python types allowed for (de)serializing data with Paradict classes and functi...
82 | - [adapters](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
83 | - [bin\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
84 | - [bin\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
85 | - [bool\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
86 | - [bool\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
87 | - [complex\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
88 | - [complex\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
89 | - [date\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
90 | - [date\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
91 | - [datetime\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
92 | - [datetime\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
93 | - [dict\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
94 | - [dict\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
95 | - [float\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
96 | - [float\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
97 | - [grid\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
98 | - [grid\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
99 | - [int\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
100 | - [int\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
101 | - [list\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
102 | - [list\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
103 | - [obj\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
104 | - [obj\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
105 | - [set\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
106 | - [set\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
107 | - [str\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
108 | - [str\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
109 | - [time\_type](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
110 | - [time\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#properties-table); _getter, setter_
111 | - [adapt](/docs/api/modules/jinbase/__init__/class-TypeRef.md#adapt): Checks the 'adapters' attribute to find out if there is an adapter function registered for the type of the data argument. Then, ...
112 | - [check](/docs/api/modules/jinbase/__init__/class-TypeRef.md#check): This function accepts as argument a Python type, and return a Datatype instance if the type is supported/registered, else return...
113 | - [\_create\_map](/docs/api/modules/jinbase/__init__/class-TypeRef.md#_create_map): No docstring.
114 | - [\_update\_types](/docs/api/modules/jinbase/__init__/class-TypeRef.md#_update_types): No docstring.
115 |
116 | Back to top
117 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/__init__/class-Jinbase.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/__init__/README.md) | [Source](/src/jinbase/__init__.py)
3 |
4 | # Class Jinbase
5 | > Module: [jinbase.\_\_init\_\_](/docs/api/modules/jinbase/__init__/README.md)
6 | >
7 | > Class: **Jinbase**
8 | >
9 | > Inheritance: `object`
10 |
11 | The Jinbase class. A Jinbase object is intended to
12 | be directly instantiated by the user.
13 |
14 | ## Properties table
15 | Here are properties exposed in the class:
16 |
17 | | Property | Methods | Description |
18 | | --- | --- | --- |
19 | | chunk\_size | _getter_ | No docstring. |
20 | | created\_at | _getter_ | No docstring. |
21 | | creation\_dt | _getter_ | No docstring. |
22 | | dbc | _getter_ | The instance of litedbc.LiteDBC |
23 | | depot | _getter_ | No docstring. |
24 | | filename | _getter_ | No docstring. |
25 | | in\_memory | _getter_ | No docstring. |
26 | | is\_closed | _getter_ | No docstring. |
27 | | is\_destroyed | _getter_ | No docstring. |
28 | | is\_new | _getter_ | No docstring. |
29 | | is\_readonly | _getter_ | No docstring. |
30 | | kv | _getter_ | No docstring. |
31 | | queue | _getter_ | No docstring. |
32 | | stack | _getter_ | No docstring. |
33 | | timeout | _getter_ | No docstring. |
34 | | timestamp\_precision | _getter_ | No docstring. |
35 | | type\_ref | _getter_ | No docstring. |
36 | | version | _getter_ | No docstring. |
37 |
38 | Back to top
39 |
40 | # Methods within class
41 | Here are methods exposed in the class:
42 | - [\_\_init\_\_](#__init__)
43 | - [backup](#backup)
44 | - [close](#close)
45 | - [copy](#copy)
46 | - [count\_bytes](#count_bytes)
47 | - [count\_chunks](#count_chunks)
48 | - [count\_records](#count_records)
49 | - [destroy](#destroy)
50 | - [get\_journal\_mode](#get_journal_mode)
51 | - [get\_locking\_mode](#get_locking_mode)
52 | - [get\_sync\_mode](#get_sync_mode)
53 | - [interrupt](#interrupt)
54 | - [iterdump](#iterdump)
55 | - [latest](#latest)
56 | - [now](#now)
57 | - [now\_dt](#now_dt)
58 | - [read\_transaction](#read_transaction)
59 | - [scan](#scan)
60 | - [set\_journal\_mode](#set_journal_mode)
61 | - [set\_locking\_mode](#set_locking_mode)
62 | - [set\_progress\_handler](#set_progress_handler)
63 | - [set\_sync\_mode](#set_sync_mode)
64 | - [set\_trace\_callback](#set_trace_callback)
65 | - [transaction](#transaction)
66 | - [vacuum](#vacuum)
67 | - [vacuum\_into](#vacuum_into)
68 | - [write\_transaction](#write_transaction)
69 |
70 | ## \_\_init\_\_
71 | Init.
72 |
73 | ```python
74 | def __init__(self, filename=None, *, auto_create=True, is_readonly=False, timeout=5.0, type_ref=None, chunk_size=1048576, timestamp_precision=):
75 | ...
76 | ```
77 |
78 | | Parameter | Description |
79 | | --- | --- |
80 | | filename | The filename of the Jinbase database. If the pointed file doesn't exist, it will be created if `auto_create` is set to True. |
81 | | auto\_create | Boolean to tell whether a nonexistent database file should automatically be created or not. Defaults to True. |
82 | | is\_readonly | Boolean to tell whether the database connection should be in readonly or not. |
83 | | timeout | Timeout in seconds for all database operations. Defaults to the value of `jinbase.TIMEOUT` |
84 | | type\_ref | A paradict.TypeRef instance |
85 | | chunk\_size | Chunk size in bytes. Defaults to `jinbase.CHUNK_SIZE`. Note that this value is only relevant when the Jinbase tables are created. |
86 | | timestamp\_precision | An instance of the `jinbase.TimestampPrecision` namedtuple. Defaults to `jinbase.TIMESTAMP_PRECISION`. Note that this value is only relevant when the Jinbase tables are created. |
87 |
88 | Back to top
89 |
90 | ## backup
91 | No docstring
92 |
93 | ```python
94 | def backup(self, dst, *, pages=-1, progress=None, sleep=0.25):
95 | ...
96 | ```
97 |
98 | Back to top
99 |
100 | ## close
101 | Close the connection
102 |
103 | ```python
104 | def close(self):
105 | ...
106 | ```
107 |
108 | Back to top
109 |
110 | ## copy
111 | Create a new Jinbase instance that
112 | points to the same database file
113 |
114 | ```python
115 | def copy(self):
116 | ...
117 | ```
118 |
119 | Back to top
120 |
121 | ## count\_bytes
122 | No docstring
123 |
124 | ```python
125 | def count_bytes(self):
126 | ...
127 | ```
128 |
129 | Back to top
130 |
131 | ## count\_chunks
132 | No docstring
133 |
134 | ```python
135 | def count_chunks(self):
136 | ...
137 | ```
138 |
139 | Back to top
140 |
141 | ## count\_records
142 | No docstring
143 |
144 | ```python
145 | def count_records(self):
146 | ...
147 | ```
148 |
149 | Back to top
150 |
151 | ## destroy
152 | Destroy the database file
153 |
154 | ```python
155 | def destroy(self):
156 | ...
157 | ```
158 |
159 | Back to top
160 |
161 | ## get\_journal\_mode
162 | No docstring
163 |
164 | ```python
165 | def get_journal_mode(self):
166 | ...
167 | ```
168 |
169 | Back to top
170 |
171 | ## get\_locking\_mode
172 | No docstring
173 |
174 | ```python
175 | def get_locking_mode(self):
176 | ...
177 | ```
178 |
179 | Back to top
180 |
181 | ## get\_sync\_mode
182 | No docstring
183 |
184 | ```python
185 | def get_sync_mode(self):
186 | ...
187 | ```
188 |
189 | Back to top
190 |
191 | ## interrupt
192 | No docstring
193 |
194 | ```python
195 | def interrupt(self):
196 | ...
197 | ```
198 |
199 | Back to top
200 |
201 | ## iterdump
202 | Returns an iterator to the dump of the database
203 | in an SQL text format
204 |
205 | ```python
206 | def iterdump(self):
207 | ...
208 | ```
209 |
210 | Back to top
211 |
212 | ## latest
213 | Get the utc datetime of the latest operation.
214 |
215 | ```python
216 | def latest(self):
217 | ...
218 | ```
219 |
220 | ### Value to return
221 | A utc instance of `datetime.datetime`
222 |
223 | Back to top
224 |
225 | ## now
226 | Get the current utc datetime.
227 |
228 | ```python
229 | @staticmethod
230 | def now():
231 | ...
232 | ```
233 |
234 | ### Value to return
235 | A utc instance of `datetime.datetime`
236 |
237 | Back to top
238 |
239 | ## now\_dt
240 | Get the current utc datetime.
241 |
242 | ```python
243 | @staticmethod
244 | def now_dt():
245 | ...
246 | ```
247 |
248 | ### Value to return
249 | A utc string
250 |
251 | Back to top
252 |
253 | ## read\_transaction
254 | No docstring
255 |
256 | ```python
257 | def read_transaction(self):
258 | ...
259 | ```
260 |
261 | Back to top
262 |
263 | ## scan
264 | Scan the Jinbase database
265 |
266 | ```python
267 | def scan(self):
268 | ...
269 | ```
270 |
271 | ### Value to return
272 | A dictionary object whose keys are jinbase.Model namedtuples
273 | and values are tuples of the total record count and total byte count.
274 |
275 | Back to top
276 |
277 | ## set\_journal\_mode
278 | No docstring
279 |
280 | ```python
281 | def set_journal_mode(self, journal_mode):
282 | ...
283 | ```
284 |
285 | Back to top
286 |
287 | ## set\_locking\_mode
288 | No docstring
289 |
290 | ```python
291 | def set_locking_mode(self, locking_mode):
292 | ...
293 | ```
294 |
295 | Back to top
296 |
297 | ## set\_progress\_handler
298 | No docstring
299 |
300 | ```python
301 | def set_progress_handler(self, callback, n):
302 | ...
303 | ```
304 |
305 | Back to top
306 |
307 | ## set\_sync\_mode
308 | No docstring
309 |
310 | ```python
311 | def set_sync_mode(self, sync_mode):
312 | ...
313 | ```
314 |
315 | Back to top
316 |
317 | ## set\_trace\_callback
318 | No docstring
319 |
320 | ```python
321 | def set_trace_callback(self, callback):
322 | ...
323 | ```
324 |
325 | Back to top
326 |
327 | ## transaction
328 | No docstring
329 |
330 | ```python
331 | def transaction(self, transaction_mode=):
332 | ...
333 | ```
334 |
335 | Back to top
336 |
337 | ## vacuum
338 | Vacuum the database
339 |
340 | ```python
341 | def vacuum(self):
342 | ...
343 | ```
344 |
345 | Back to top
346 |
347 | ## vacuum\_into
348 | Vacuum into a file whose name is provided via `dst`.
349 |
350 | ```python
351 | def vacuum_into(self, dst):
352 | ...
353 | ```
354 |
355 | Back to top
356 |
357 | ## write\_transaction
358 | No docstring
359 |
360 | ```python
361 | def write_transaction(self):
362 | ...
363 | ```
364 |
365 | Back to top
366 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/__init__/class-Model.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/__init__/README.md) | [Source](/src/jinbase/__init__.py)
3 |
4 | # Class Model
5 | > Module: [jinbase.\_\_init\_\_](/docs/api/modules/jinbase/__init__/README.md)
6 | >
7 | > Class: **Model**
8 | >
9 | > Inheritance: `enum.Enum`
10 |
11 | Create a collection of name/value pairs.
12 |
13 | Example enumeration:
14 |
15 | >>> class Color(Enum):
16 | ... RED = 1
17 | ... BLUE = 2
18 | ... GREEN = 3
19 |
20 | Access them by:
21 |
22 | - attribute access:
23 |
24 | >>> Color.RED
25 |
26 |
27 | - value lookup:
28 |
29 | >>> Color(1)
30 |
31 |
32 | - name lookup:
33 |
34 | >>> Color['RED']
35 |
36 |
37 | Enumerations can be iterated over, and know how many members they have:
38 |
39 | >>> len(Color)
40 | 3
41 |
42 | >>> list(Color)
43 |
44 | ## Fields table
45 | Here are fields exposed in the class:
46 |
47 | | Field | Value |
48 | | --- | --- |
49 | | KV | `1` |
50 | | DEPOT | `2` |
51 | | QUEUE | `3` |
52 | | STACK | `4` |
53 |
54 | Back to top
55 |
56 | # Methods within class
57 | Here are methods exposed in the class:
58 | - [\_\_init\_\_](#__init__)
59 | - [\_generate\_next\_value\_](#_generate_next_value_)
60 | - [\_missing\_](#_missing_)
61 |
62 | ## \_\_init\_\_
63 | Initialize self. See help(type(self)) for accurate signature.
64 |
65 | ```python
66 | def __init__(self, *args, **kwds):
67 | ...
68 | ```
69 |
70 | Back to top
71 |
72 | ## \_generate\_next\_value\_
73 | Generate the next value when not given.
74 |
75 | name: the name of the member
76 | start: the initial start value or None
77 | count: the number of existing members
78 | last_values: the list of values assigned
79 |
80 | ```python
81 | @staticmethod
82 | def _generate_next_value_(name, start, count, last_values):
83 | ...
84 | ```
85 |
86 | Back to top
87 |
88 | ## \_missing\_
89 | No docstring
90 |
91 | ```python
92 | @classmethod
93 | def _missing_(value):
94 | ...
95 | ```
96 |
97 | Back to top
98 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/__init__/class-RecordInfo.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/__init__/README.md) | [Source](/src/jinbase/__init__.py)
3 |
4 | # Class RecordInfo
5 | > Module: [jinbase.\_\_init\_\_](/docs/api/modules/jinbase/__init__/README.md)
6 | >
7 | > Class: **RecordInfo**
8 | >
9 | > Inheritance: `tuple`
10 |
11 | Named tuple returned by store.info()
12 |
13 | ## Fields table
14 | Here are fields exposed in the class:
15 |
16 | | Field | Description |
17 | | --- | --- |
18 | | uid | Alias for field number 0 |
19 | | datatype | Alias for field number 1 |
20 | | created\_at | Alias for field number 2 |
21 |
22 | Back to top
23 |
24 | # Methods within class
25 | Here are methods exposed in the class:
26 | - [\_asdict](#_asdict)
27 | - [\_make](#_make)
28 | - [\_replace](#_replace)
29 |
30 | ## \_asdict
31 | Return a new dict which maps field names to their values.
32 |
33 | ```python
34 | def _asdict(self):
35 | ...
36 | ```
37 |
38 | Back to top
39 |
40 | ## \_make
41 | Make a new RecordInfo object from a sequence or iterable
42 |
43 | ```python
44 | @classmethod
45 | def _make(iterable):
46 | ...
47 | ```
48 |
49 | Back to top
50 |
51 | ## \_replace
52 | Return a new RecordInfo object replacing specified fields with new values
53 |
54 | ```python
55 | def _replace(self, /, **kwds):
56 | ...
57 | ```
58 |
59 | Back to top
60 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/__init__/class-TimestampPrecision.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/__init__/README.md) | [Source](/src/jinbase/__init__.py)
3 |
4 | # Class TimestampPrecision
5 | > Module: [jinbase.\_\_init\_\_](/docs/api/modules/jinbase/__init__/README.md)
6 | >
7 | > Class: **TimestampPrecision**
8 | >
9 | > Inheritance: `enum.Enum`
10 |
11 | Create a collection of name/value pairs.
12 |
13 | Example enumeration:
14 |
15 | >>> class Color(Enum):
16 | ... RED = 1
17 | ... BLUE = 2
18 | ... GREEN = 3
19 |
20 | Access them by:
21 |
22 | - attribute access:
23 |
24 | >>> Color.RED
25 |
26 |
27 | - value lookup:
28 |
29 | >>> Color(1)
30 |
31 |
32 | - name lookup:
33 |
34 | >>> Color['RED']
35 |
36 |
37 | Enumerations can be iterated over, and know how many members they have:
38 |
39 | >>> len(Color)
40 | 3
41 |
42 | >>> list(Color)
43 |
44 | ## Fields table
45 | Here are fields exposed in the class:
46 |
47 | | Field | Value |
48 | | --- | --- |
49 | | SECONDS | `0` |
50 | | MILLISECONDS | `3` |
51 | | MICROSECONDS | `6` |
52 | | NANOSECONDS | `9` |
53 |
54 | Back to top
55 |
56 | # Methods within class
57 | Here are methods exposed in the class:
58 | - [\_\_init\_\_](#__init__)
59 | - [\_generate\_next\_value\_](#_generate_next_value_)
60 | - [\_missing\_](#_missing_)
61 |
62 | ## \_\_init\_\_
63 | Initialize self. See help(type(self)) for accurate signature.
64 |
65 | ```python
66 | def __init__(self, *args, **kwds):
67 | ...
68 | ```
69 |
70 | Back to top
71 |
72 | ## \_generate\_next\_value\_
73 | Generate the next value when not given.
74 |
75 | name: the name of the member
76 | start: the initial start value or None
77 | count: the number of existing members
78 | last_values: the list of values assigned
79 |
80 | ```python
81 | @staticmethod
82 | def _generate_next_value_(name, start, count, last_values):
83 | ...
84 | ```
85 |
86 | Back to top
87 |
88 | ## \_missing\_
89 | No docstring
90 |
91 | ```python
92 | @classmethod
93 | def _missing_(value):
94 | ...
95 | ```
96 |
97 | Back to top
98 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/__init__/class-TypeRef.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/__init__/README.md) | [Source](/src/jinbase/__init__.py)
3 |
4 | # Class TypeRef
5 | > Module: [jinbase.\_\_init\_\_](/docs/api/modules/jinbase/__init__/README.md)
6 | >
7 | > Class: **TypeRef**
8 | >
9 | > Inheritance: `object`
10 |
11 | This class represents a mechanism for customizing
12 | Python types allowed for (de)serializing data with Paradict classes and functions.
13 | For example, one might want to only use Python OrderedDict instead of the regular
14 | dict. In this case, just create a TypeRef instance, and make sure that you
15 | set the dict_type attribute via the construction or a property.
16 |
17 | ```python
18 | type_ref = TypeRef(dict_type=OrderedDict)
19 | ```
20 |
21 | Still with this class, one could 'adapt' some exotic datatype so it will
22 | conform with Python datatypes allowed in Paradict (de)serialization.
23 | To do so, set the adapters attribute like this:
24 |
25 | ```python
26 | adapters = {MyExoticType1: adapterFunction1, MyExoticType2: adapterFunction2}
27 | type_ref = TypeRef(adapters=adapters)
28 | ```
29 |
30 | ## Properties table
31 | Here are properties exposed in the class:
32 |
33 | | Property | Methods | Description |
34 | | --- | --- | --- |
35 | | adapters | _getter, setter_ | No docstring. |
36 | | bin\_type | _getter, setter_ | No docstring. |
37 | | bin\_types | _getter, setter_ | No docstring. |
38 | | bool\_type | _getter, setter_ | No docstring. |
39 | | bool\_types | _getter, setter_ | No docstring. |
40 | | complex\_type | _getter, setter_ | No docstring. |
41 | | complex\_types | _getter, setter_ | No docstring. |
42 | | date\_type | _getter, setter_ | No docstring. |
43 | | date\_types | _getter, setter_ | No docstring. |
44 | | datetime\_type | _getter, setter_ | No docstring. |
45 | | datetime\_types | _getter, setter_ | No docstring. |
46 | | dict\_type | _getter, setter_ | No docstring. |
47 | | dict\_types | _getter, setter_ | No docstring. |
48 | | float\_type | _getter, setter_ | No docstring. |
49 | | float\_types | _getter, setter_ | No docstring. |
50 | | grid\_type | _getter, setter_ | No docstring. |
51 | | grid\_types | _getter, setter_ | No docstring. |
52 | | int\_type | _getter, setter_ | No docstring. |
53 | | int\_types | _getter, setter_ | No docstring. |
54 | | list\_type | _getter, setter_ | No docstring. |
55 | | list\_types | _getter, setter_ | No docstring. |
56 | | obj\_type | _getter, setter_ | No docstring. |
57 | | obj\_types | _getter, setter_ | No docstring. |
58 | | set\_type | _getter, setter_ | No docstring. |
59 | | set\_types | _getter, setter_ | No docstring. |
60 | | str\_type | _getter, setter_ | No docstring. |
61 | | str\_types | _getter, setter_ | No docstring. |
62 | | time\_type | _getter, setter_ | No docstring. |
63 | | time\_types | _getter, setter_ | No docstring. |
64 |
65 | Back to top
66 |
67 | # Methods within class
68 | Here are methods exposed in the class:
69 | - [\_\_init\_\_](#__init__)
70 | - [adapt](#adapt)
71 | - [check](#check)
72 | - [\_create\_map](#_create_map)
73 | - [\_update\_types](#_update_types)
74 |
75 | ## \_\_init\_\_
76 | Initialize self. See help(type(self)) for accurate signature.
77 |
78 | ```python
79 | def __init__(self, adapters=None, dict_type=None, list_type=None, set_type=None, obj_type=None, dict_types=None, list_types=None, set_types=None, obj_types=None, bin_type=None, bool_type=None, complex_type=None, date_type=None, datetime_type=None, float_type=None, grid_type=None, int_type=None, str_type=None, time_type=None, bin_types=None, bool_types=None, complex_types=None, date_types=None, datetime_types=None, float_types=None, grid_types=None, int_types=None, str_types=None, time_types=None):
80 | ...
81 | ```
82 |
83 | Back to top
84 |
85 | ## adapt
86 | Checks the 'adapters' attribute to find out if there is
87 | an adapter function registered for the type of the data argument.
88 | Then, calls the adapter on the value.
89 |
90 | ```python
91 | def adapt(self, value):
92 | ...
93 | ```
94 |
95 | | Parameter | Description |
96 | | --- | --- |
97 | | value | the data value to adapt is an arbitrary Python object |
98 |
99 | ### Value to return
100 | Returns the adapted value or the same value if no adapter is registered for its type
101 |
102 | Back to top
103 |
104 | ## check
105 | This function accepts as argument a Python type, and return
106 | a Datatype instance if the type is supported/registered, else returns None
107 |
108 | ```python
109 | def check(self, dtype):
110 | ...
111 | ```
112 |
113 | Back to top
114 |
115 | ## \_create\_map
116 | No docstring
117 |
118 | ```python
119 | def _create_map(self):
120 | ...
121 | ```
122 |
123 | Back to top
124 |
125 | ## \_update\_types
126 | No docstring
127 |
128 | ```python
129 | def _update_types(self, name, datatype):
130 | ...
131 | ```
132 |
133 | Back to top
134 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/__init__/fields.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/__init__/README.md) | [Source](/src/jinbase/__init__.py)
3 |
4 | # Fields within module
5 | > Module: [jinbase.\_\_init\_\_](/docs/api/modules/jinbase/__init__/README.md)
6 |
7 | Here are fields exposed in the module:
8 |
9 | | Field | Value |
10 | | --- | --- |
11 | | CHUNK\_SIZE | `1048576` |
12 | | DATETIME\_FORMAT | `'%Y-%m-%d %H:%M:%S.%fZ'` |
13 | | JINBASE\_HOME | `'/home/alex/JinbaseHome'` |
14 | | JINBASE\_VERSION | `1` |
15 | | TIMEOUT | `5.0` |
16 | | TIMESTAMP\_PRECISION | `` |
17 | | USER\_HOME | `'/home/alex'` |
18 |
19 | Back to top
20 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/blob/__init__/README.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | Module | [Source](/src/jinbase/blob/__init__.py)
3 |
4 | # Module Overview
5 | > Module: **jinbase.blob.\_\_init\_\_**
6 |
7 | The Blob class is defined here.
8 |
9 | ## Classes
10 | - [**Blob**](/docs/api/modules/jinbase/blob/__init__/class-Blob.md): The Blob class allows a Read access to the blobs of Jinbase records. This class isn't intended to be directly instantiated by th...
11 | - [close](/docs/api/modules/jinbase/blob/__init__/class-Blob.md#close): Close this Blob instance. Note that this method is automatically called by the Store's open_blob method.
12 | - [read](/docs/api/modules/jinbase/blob/__init__/class-Blob.md#read): Read the blob.
13 | - [seek](/docs/api/modules/jinbase/blob/__init__/class-Blob.md#seek): Move the cursor to another position
14 | - [tell](/docs/api/modules/jinbase/blob/__init__/class-Blob.md#tell): Returns the current position of the cursor
15 | - [write](/docs/api/modules/jinbase/blob/__init__/class-Blob.md#write): Jinbase doesn't allow Writes on blobs
16 | - [\_get\_blob\_io\_file](/docs/api/modules/jinbase/blob/__init__/class-Blob.md#_get_blob_io_file): No docstring.
17 | - [\_get\_chunk](/docs/api/modules/jinbase/blob/__init__/class-Blob.md#_get_chunk): No docstring.
18 | - [\_read](/docs/api/modules/jinbase/blob/__init__/class-Blob.md#_read): No docstring.
19 |
20 | Back to top
21 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/blob/__init__/class-Blob.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/blob/__init__/README.md) | [Source](/src/jinbase/blob/__init__.py)
3 |
4 | # Class Blob
5 | > Module: [jinbase.blob.\_\_init\_\_](/docs/api/modules/jinbase/blob/__init__/README.md)
6 | >
7 | > Class: **Blob**
8 | >
9 | > Inheritance: `object`
10 |
11 | The Blob class allows a Read access to the blobs of Jinbase records.
12 | This class isn't intended to be directly instantiated by the user.
13 |
14 | # Methods within class
15 | Here are methods exposed in the class:
16 | - [\_\_init\_\_](#__init__)
17 | - [close](#close)
18 | - [read](#read)
19 | - [seek](#seek)
20 | - [tell](#tell)
21 | - [write](#write)
22 | - [\_get\_blob\_io\_file](#_get_blob_io_file)
23 | - [\_get\_chunk](#_get_chunk)
24 | - [\_read](#_read)
25 |
26 | ## \_\_init\_\_
27 | Initialization.
28 |
29 | ```python
30 | def __init__(self, store, record_id, n_bytes, n_chunks):
31 | ...
32 | ```
33 |
34 | | Parameter | Description |
35 | | --- | --- |
36 | | store | Store instance. |
37 | | record\_id | The record's uid. |
38 | | n\_bytes | The size of the blob in bytes. |
39 | | n\_chunks | The number of chunks. |
40 |
41 | Back to top
42 |
43 | ## close
44 | Close this Blob instance. Note that this method
45 | is automatically called by the Store's open_blob method.
46 |
47 | ```python
48 | def close(self):
49 | ...
50 | ```
51 |
52 | Back to top
53 |
54 | ## read
55 | Read the blob.
56 |
57 | ```python
58 | def read(self, length=-1, /):
59 | ...
60 | ```
61 |
62 | | Parameter | Description |
63 | | --- | --- |
64 | | length | The number of bytes to read. Defaults to -1 to mean the entire blob. Note that the cursor moves as reads are done. |
65 |
66 | ### Value to return
67 | Returns bytes or an empty byte.
68 |
69 | Back to top
70 |
71 | ## seek
72 | Move the cursor to another position
73 |
74 | ```python
75 | def seek(self, offset, origin=0, /):
76 | ...
77 | ```
78 |
79 | | Parameter | Description |
80 | | --- | --- |
81 | | offset | Offset value |
82 | | origin | os.SEEK_SET, os.SEEK_CUR, or os.SEEK_END. Note that os.SEEK_END referes to position beyond the last character of the file, not the last character itself. |
83 |
84 | Back to top
85 |
86 | ## tell
87 | Returns the current position of the cursor
88 |
89 | ```python
90 | def tell(self):
91 | ...
92 | ```
93 |
94 | Back to top
95 |
96 | ## write
97 | Jinbase doesn't allow Writes on blobs
98 |
99 | ```python
100 | def write(self, data, /):
101 | ...
102 | ```
103 |
104 | Back to top
105 |
106 | ## \_get\_blob\_io\_file
107 | No docstring
108 |
109 | ```python
110 | def _get_blob_io_file(self, chunk_index):
111 | ...
112 | ```
113 |
114 | Back to top
115 |
116 | ## \_get\_chunk
117 | No docstring
118 |
119 | ```python
120 | def _get_chunk(self, blob_slice):
121 | ...
122 | ```
123 |
124 | Back to top
125 |
126 | ## \_read
127 | No docstring
128 |
129 | ```python
130 | def _read(self, position, length):
131 | ...
132 | ```
133 |
134 | Back to top
135 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/const/__init__/README.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | Module | [Source](/src/jinbase/const/__init__.py)
3 |
4 | # Module Overview
5 | > Module: **jinbase.const.\_\_init\_\_**
6 |
7 | Project-wide constants are defined in this module.
8 |
9 | ## Fields
10 | - [**All fields**](/docs/api/modules/jinbase/const/__init__/fields.md)
11 | - CHUNK\_SIZE = `1048576`
12 | - DATETIME\_FORMAT = `'%Y-%m-%d %H:%M:%S.%fZ'`
13 | - JINBASE\_HOME = `'/home/alex/JinbaseHome'`
14 | - JINBASE\_VERSION = `1`
15 | - TIMEOUT = `5.0`
16 | - TIMESTAMP\_PRECISION = ``
17 | - USER\_HOME = `'/home/alex'`
18 |
19 | Back to top
20 |
21 | ## Classes
22 | - [**Model**](/docs/api/modules/jinbase/const/__init__/class-Model.md): Create a collection of name/value pairs.
23 | - KV = `1`
24 | - DEPOT = `2`
25 | - QUEUE = `3`
26 | - STACK = `4`
27 | - [**StorageUnit**](/docs/api/modules/jinbase/const/__init__/class-StorageUnit.md): Create a collection of name/value pairs.
28 | - BYTE = `'B'`
29 | - KIBIBYTE = `'KiB'`
30 | - MEBIBYTE = `'MiB'`
31 | - GIBIBYTE = `'GiB'`
32 | - TEBIBYTE = `'TiB'`
33 | - [**TimeUnit**](/docs/api/modules/jinbase/const/__init__/class-TimeUnit.md): Create a collection of name/value pairs.
34 | - SECOND = `'sec'`
35 | - MINUTE = `'min'`
36 | - HOUR = `'hour'`
37 | - DAY = `'day'`
38 | - WEEK = `'week'`
39 | - [**TimestampPrecision**](/docs/api/modules/jinbase/const/__init__/class-TimestampPrecision.md): Create a collection of name/value pairs.
40 | - SECONDS = `0`
41 | - MILLISECONDS = `3`
42 | - MICROSECONDS = `6`
43 | - NANOSECONDS = `9`
44 |
45 | Back to top
46 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/const/__init__/class-Model.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/const/__init__/README.md) | [Source](/src/jinbase/const/__init__.py)
3 |
4 | # Class Model
5 | > Module: [jinbase.const.\_\_init\_\_](/docs/api/modules/jinbase/const/__init__/README.md)
6 | >
7 | > Class: **Model**
8 | >
9 | > Inheritance: `enum.Enum`
10 |
11 | Create a collection of name/value pairs.
12 |
13 | Example enumeration:
14 |
15 | >>> class Color(Enum):
16 | ... RED = 1
17 | ... BLUE = 2
18 | ... GREEN = 3
19 |
20 | Access them by:
21 |
22 | - attribute access:
23 |
24 | >>> Color.RED
25 |
26 |
27 | - value lookup:
28 |
29 | >>> Color(1)
30 |
31 |
32 | - name lookup:
33 |
34 | >>> Color['RED']
35 |
36 |
37 | Enumerations can be iterated over, and know how many members they have:
38 |
39 | >>> len(Color)
40 | 3
41 |
42 | >>> list(Color)
43 |
44 | ## Fields table
45 | Here are fields exposed in the class:
46 |
47 | | Field | Value |
48 | | --- | --- |
49 | | KV | `1` |
50 | | DEPOT | `2` |
51 | | QUEUE | `3` |
52 | | STACK | `4` |
53 |
54 | Back to top
55 |
56 | # Methods within class
57 | Here are methods exposed in the class:
58 | - [\_\_init\_\_](#__init__)
59 | - [\_generate\_next\_value\_](#_generate_next_value_)
60 | - [\_missing\_](#_missing_)
61 |
62 | ## \_\_init\_\_
63 | Initialize self. See help(type(self)) for accurate signature.
64 |
65 | ```python
66 | def __init__(self, *args, **kwds):
67 | ...
68 | ```
69 |
70 | Back to top
71 |
72 | ## \_generate\_next\_value\_
73 | Generate the next value when not given.
74 |
75 | name: the name of the member
76 | start: the initial start value or None
77 | count: the number of existing members
78 | last_values: the list of values assigned
79 |
80 | ```python
81 | @staticmethod
82 | def _generate_next_value_(name, start, count, last_values):
83 | ...
84 | ```
85 |
86 | Back to top
87 |
88 | ## \_missing\_
89 | No docstring
90 |
91 | ```python
92 | @classmethod
93 | def _missing_(value):
94 | ...
95 | ```
96 |
97 | Back to top
98 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/const/__init__/class-StorageUnit.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/const/__init__/README.md) | [Source](/src/jinbase/const/__init__.py)
3 |
4 | # Class StorageUnit
5 | > Module: [jinbase.const.\_\_init\_\_](/docs/api/modules/jinbase/const/__init__/README.md)
6 | >
7 | > Class: **StorageUnit**
8 | >
9 | > Inheritance: `enum.Enum`
10 |
11 | Create a collection of name/value pairs.
12 |
13 | Example enumeration:
14 |
15 | >>> class Color(Enum):
16 | ... RED = 1
17 | ... BLUE = 2
18 | ... GREEN = 3
19 |
20 | Access them by:
21 |
22 | - attribute access:
23 |
24 | >>> Color.RED
25 |
26 |
27 | - value lookup:
28 |
29 | >>> Color(1)
30 |
31 |
32 | - name lookup:
33 |
34 | >>> Color['RED']
35 |
36 |
37 | Enumerations can be iterated over, and know how many members they have:
38 |
39 | >>> len(Color)
40 | 3
41 |
42 | >>> list(Color)
43 |
44 | ## Fields table
45 | Here are fields exposed in the class:
46 |
47 | | Field | Value |
48 | | --- | --- |
49 | | BYTE | `'B'` |
50 | | KIBIBYTE | `'KiB'` |
51 | | MEBIBYTE | `'MiB'` |
52 | | GIBIBYTE | `'GiB'` |
53 | | TEBIBYTE | `'TiB'` |
54 |
55 | Back to top
56 |
57 | # Methods within class
58 | Here are methods exposed in the class:
59 | - [\_\_init\_\_](#__init__)
60 | - [\_generate\_next\_value\_](#_generate_next_value_)
61 | - [\_missing\_](#_missing_)
62 |
63 | ## \_\_init\_\_
64 | Initialize self. See help(type(self)) for accurate signature.
65 |
66 | ```python
67 | def __init__(self, *args, **kwds):
68 | ...
69 | ```
70 |
71 | Back to top
72 |
73 | ## \_generate\_next\_value\_
74 | Generate the next value when not given.
75 |
76 | name: the name of the member
77 | start: the initial start value or None
78 | count: the number of existing members
79 | last_values: the list of values assigned
80 |
81 | ```python
82 | @staticmethod
83 | def _generate_next_value_(name, start, count, last_values):
84 | ...
85 | ```
86 |
87 | Back to top
88 |
89 | ## \_missing\_
90 | No docstring
91 |
92 | ```python
93 | @classmethod
94 | def _missing_(value):
95 | ...
96 | ```
97 |
98 | Back to top
99 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/const/__init__/class-TimeUnit.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/const/__init__/README.md) | [Source](/src/jinbase/const/__init__.py)
3 |
4 | # Class TimeUnit
5 | > Module: [jinbase.const.\_\_init\_\_](/docs/api/modules/jinbase/const/__init__/README.md)
6 | >
7 | > Class: **TimeUnit**
8 | >
9 | > Inheritance: `enum.Enum`
10 |
11 | Create a collection of name/value pairs.
12 |
13 | Example enumeration:
14 |
15 | >>> class Color(Enum):
16 | ... RED = 1
17 | ... BLUE = 2
18 | ... GREEN = 3
19 |
20 | Access them by:
21 |
22 | - attribute access:
23 |
24 | >>> Color.RED
25 |
26 |
27 | - value lookup:
28 |
29 | >>> Color(1)
30 |
31 |
32 | - name lookup:
33 |
34 | >>> Color['RED']
35 |
36 |
37 | Enumerations can be iterated over, and know how many members they have:
38 |
39 | >>> len(Color)
40 | 3
41 |
42 | >>> list(Color)
43 |
44 | ## Fields table
45 | Here are fields exposed in the class:
46 |
47 | | Field | Value |
48 | | --- | --- |
49 | | SECOND | `'sec'` |
50 | | MINUTE | `'min'` |
51 | | HOUR | `'hour'` |
52 | | DAY | `'day'` |
53 | | WEEK | `'week'` |
54 |
55 | Back to top
56 |
57 | # Methods within class
58 | Here are methods exposed in the class:
59 | - [\_\_init\_\_](#__init__)
60 | - [\_generate\_next\_value\_](#_generate_next_value_)
61 | - [\_missing\_](#_missing_)
62 |
63 | ## \_\_init\_\_
64 | Initialize self. See help(type(self)) for accurate signature.
65 |
66 | ```python
67 | def __init__(self, *args, **kwds):
68 | ...
69 | ```
70 |
71 | Back to top
72 |
73 | ## \_generate\_next\_value\_
74 | Generate the next value when not given.
75 |
76 | name: the name of the member
77 | start: the initial start value or None
78 | count: the number of existing members
79 | last_values: the list of values assigned
80 |
81 | ```python
82 | @staticmethod
83 | def _generate_next_value_(name, start, count, last_values):
84 | ...
85 | ```
86 |
87 | Back to top
88 |
89 | ## \_missing\_
90 | No docstring
91 |
92 | ```python
93 | @classmethod
94 | def _missing_(value):
95 | ...
96 | ```
97 |
98 | Back to top
99 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/const/__init__/class-TimestampPrecision.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/const/__init__/README.md) | [Source](/src/jinbase/const/__init__.py)
3 |
4 | # Class TimestampPrecision
5 | > Module: [jinbase.const.\_\_init\_\_](/docs/api/modules/jinbase/const/__init__/README.md)
6 | >
7 | > Class: **TimestampPrecision**
8 | >
9 | > Inheritance: `enum.Enum`
10 |
11 | Create a collection of name/value pairs.
12 |
13 | Example enumeration:
14 |
15 | >>> class Color(Enum):
16 | ... RED = 1
17 | ... BLUE = 2
18 | ... GREEN = 3
19 |
20 | Access them by:
21 |
22 | - attribute access:
23 |
24 | >>> Color.RED
25 |
26 |
27 | - value lookup:
28 |
29 | >>> Color(1)
30 |
31 |
32 | - name lookup:
33 |
34 | >>> Color['RED']
35 |
36 |
37 | Enumerations can be iterated over, and know how many members they have:
38 |
39 | >>> len(Color)
40 | 3
41 |
42 | >>> list(Color)
43 |
44 | ## Fields table
45 | Here are fields exposed in the class:
46 |
47 | | Field | Value |
48 | | --- | --- |
49 | | SECONDS | `0` |
50 | | MILLISECONDS | `3` |
51 | | MICROSECONDS | `6` |
52 | | NANOSECONDS | `9` |
53 |
54 | Back to top
55 |
56 | # Methods within class
57 | Here are methods exposed in the class:
58 | - [\_\_init\_\_](#__init__)
59 | - [\_generate\_next\_value\_](#_generate_next_value_)
60 | - [\_missing\_](#_missing_)
61 |
62 | ## \_\_init\_\_
63 | Initialize self. See help(type(self)) for accurate signature.
64 |
65 | ```python
66 | def __init__(self, *args, **kwds):
67 | ...
68 | ```
69 |
70 | Back to top
71 |
72 | ## \_generate\_next\_value\_
73 | Generate the next value when not given.
74 |
75 | name: the name of the member
76 | start: the initial start value or None
77 | count: the number of existing members
78 | last_values: the list of values assigned
79 |
80 | ```python
81 | @staticmethod
82 | def _generate_next_value_(name, start, count, last_values):
83 | ...
84 | ```
85 |
86 | Back to top
87 |
88 | ## \_missing\_
89 | No docstring
90 |
91 | ```python
92 | @classmethod
93 | def _missing_(value):
94 | ...
95 | ```
96 |
97 | Back to top
98 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/const/__init__/fields.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/const/__init__/README.md) | [Source](/src/jinbase/const/__init__.py)
3 |
4 | # Fields within module
5 | > Module: [jinbase.const.\_\_init\_\_](/docs/api/modules/jinbase/const/__init__/README.md)
6 |
7 | Here are fields exposed in the module:
8 |
9 | | Field | Value |
10 | | --- | --- |
11 | | CHUNK\_SIZE | `1048576` |
12 | | DATETIME\_FORMAT | `'%Y-%m-%d %H:%M:%S.%fZ'` |
13 | | JINBASE\_HOME | `'/home/alex/JinbaseHome'` |
14 | | JINBASE\_VERSION | `1` |
15 | | TIMEOUT | `5.0` |
16 | | TIMESTAMP\_PRECISION | `` |
17 | | USER\_HOME | `'/home/alex'` |
18 |
19 | Back to top
20 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/__init__/README.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | Module | [Source](/src/jinbase/store/__init__.py)
3 |
4 | # Module Overview
5 | > Module: **jinbase.store.\_\_init\_\_**
6 |
7 | The abstract Store class is defined in this module.
8 |
9 | ## Classes
10 | - [**RecordInfo**](/docs/api/modules/jinbase/store/__init__/class-RecordInfo.md): Named tuple returned by store.info()
11 | - uid: Alias for field number 0
12 | - datatype: Alias for field number 1
13 | - created\_at: Alias for field number 2
14 | - [**Store**](/docs/api/modules/jinbase/store/__init__/class-Store.md): Abstract Store class intended to be subclassed by the Kv, Depot, Queue, and Stack stores
15 | - [\_abc\_impl](/docs/api/modules/jinbase/store/__init__/class-Store.md#fields-table) = `<_abc._abc_data object at 0x7eb5e3670540>`
16 | - [chunk\_size](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
17 | - [dbc](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
18 | - [filename](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
19 | - [in\_memory](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
20 | - [is\_closed](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
21 | - [is\_new](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
22 | - [is\_readonly](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
23 | - [jinbase](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
24 | - [model](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
25 | - [timeout](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
26 | - [type\_ref](/docs/api/modules/jinbase/store/__init__/class-Store.md#properties-table); _getter_
27 | - [count\_bytes](/docs/api/modules/jinbase/store/__init__/class-Store.md#count_bytes): Count all data bytes in the store.
28 | - [count\_chunks](/docs/api/modules/jinbase/store/__init__/class-Store.md#count_chunks): Count all data chunks in the store.
29 | - [count\_records](/docs/api/modules/jinbase/store/__init__/class-Store.md#count_records): Count all records in the store.
30 | - [delete\_all](/docs/api/modules/jinbase/store/__init__/class-Store.md#delete_all): Delete all records in the store
31 | - [is\_empty](/docs/api/modules/jinbase/store/__init__/class-Store.md#is_empty): Tells whether the store is empty or not
32 | - [latest](/docs/api/modules/jinbase/store/__init__/class-Store.md#latest): Retrieve the datetime of the latest write operation.
33 | - [now](/docs/api/modules/jinbase/store/__init__/class-Store.md#now): Get the current datetime.
34 | - [now\_dt](/docs/api/modules/jinbase/store/__init__/class-Store.md#now_dt): Get the current datetime.
35 | - [read\_transaction](/docs/api/modules/jinbase/store/__init__/class-Store.md#read_transaction): Context manager for executing a Read transaction.
36 | - [transaction](/docs/api/modules/jinbase/store/__init__/class-Store.md#transaction): Context manager for executing a transaction.
37 | - [write\_transaction](/docs/api/modules/jinbase/store/__init__/class-Store.md#write_transaction): Context manager for executing a Write transaction.
38 | - [\_delete\_record](/docs/api/modules/jinbase/store/__init__/class-Store.md#_delete_record): No docstring.
39 | - [\_retrieve\_data](/docs/api/modules/jinbase/store/__init__/class-Store.md#_retrieve_data): No docstring.
40 | - [\_store\_data](/docs/api/modules/jinbase/store/__init__/class-Store.md#_store_data): No docstring.
41 |
42 | Back to top
43 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/__init__/class-RecordInfo.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/store/__init__/README.md) | [Source](/src/jinbase/store/__init__.py)
3 |
4 | # Class RecordInfo
5 | > Module: [jinbase.store.\_\_init\_\_](/docs/api/modules/jinbase/store/__init__/README.md)
6 | >
7 | > Class: **RecordInfo**
8 | >
9 | > Inheritance: `tuple`
10 |
11 | Named tuple returned by store.info()
12 |
13 | ## Fields table
14 | Here are fields exposed in the class:
15 |
16 | | Field | Description |
17 | | --- | --- |
18 | | uid | Alias for field number 0 |
19 | | datatype | Alias for field number 1 |
20 | | created\_at | Alias for field number 2 |
21 |
22 | Back to top
23 |
24 | # Methods within class
25 | Here are methods exposed in the class:
26 | - [\_asdict](#_asdict)
27 | - [\_make](#_make)
28 | - [\_replace](#_replace)
29 |
30 | ## \_asdict
31 | Return a new dict which maps field names to their values.
32 |
33 | ```python
34 | def _asdict(self):
35 | ...
36 | ```
37 |
38 | Back to top
39 |
40 | ## \_make
41 | Make a new RecordInfo object from a sequence or iterable
42 |
43 | ```python
44 | @classmethod
45 | def _make(iterable):
46 | ...
47 | ```
48 |
49 | Back to top
50 |
51 | ## \_replace
52 | Return a new RecordInfo object replacing specified fields with new values
53 |
54 | ```python
55 | def _replace(self, /, **kwds):
56 | ...
57 | ```
58 |
59 | Back to top
60 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/__init__/class-Store.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/store/__init__/README.md) | [Source](/src/jinbase/store/__init__.py)
3 |
4 | # Class Store
5 | > Module: [jinbase.store.\_\_init\_\_](/docs/api/modules/jinbase/store/__init__/README.md)
6 | >
7 | > Class: **Store**
8 | >
9 | > Inheritance: `abc.ABC`
10 |
11 | Abstract Store class intended to be subclassed by the
12 | Kv, Depot, Queue, and Stack stores
13 |
14 | ## Fields table
15 | Here are fields exposed in the class:
16 |
17 | | Field | Value |
18 | | --- | --- |
19 | | \_abc\_impl | `<_abc._abc_data object at 0x7eb5e3670540>` |
20 |
21 | Back to top
22 |
23 | ## Properties table
24 | Here are properties exposed in the class:
25 |
26 | | Property | Methods | Description |
27 | | --- | --- | --- |
28 | | chunk\_size | _getter_ | No docstring. |
29 | | dbc | _getter_ | No docstring. |
30 | | filename | _getter_ | No docstring. |
31 | | in\_memory | _getter_ | No docstring. |
32 | | is\_closed | _getter_ | No docstring. |
33 | | is\_new | _getter_ | No docstring. |
34 | | is\_readonly | _getter_ | No docstring. |
35 | | jinbase | _getter_ | No docstring. |
36 | | model | _getter_ | No docstring. |
37 | | timeout | _getter_ | No docstring. |
38 | | type\_ref | _getter_ | No docstring. |
39 |
40 | Back to top
41 |
42 | # Methods within class
43 | Here are methods exposed in the class:
44 | - [\_\_init\_\_](#__init__)
45 | - [count\_bytes](#count_bytes)
46 | - [count\_chunks](#count_chunks)
47 | - [count\_records](#count_records)
48 | - [delete\_all](#delete_all)
49 | - [is\_empty](#is_empty)
50 | - [latest](#latest)
51 | - [now](#now)
52 | - [now\_dt](#now_dt)
53 | - [read\_transaction](#read_transaction)
54 | - [transaction](#transaction)
55 | - [write\_transaction](#write_transaction)
56 | - [\_delete\_record](#_delete_record)
57 | - [\_retrieve\_data](#_retrieve_data)
58 | - [\_store\_data](#_store_data)
59 |
60 | ## \_\_init\_\_
61 | Init.
62 |
63 | ```python
64 | def __init__(self, model, jinbase):
65 | ...
66 | ```
67 |
68 | | Parameter | Description |
69 | | --- | --- |
70 | | model | A Model namedtuple instance |
71 | | jinbase | Jinbase instance |
72 |
73 | Back to top
74 |
75 | ## count\_bytes
76 | Count all data bytes in the store.
77 |
78 | ```python
79 | def count_bytes(self):
80 | ...
81 | ```
82 |
83 | ### Value to return
84 | Returns the count of data bytes
85 |
86 | Back to top
87 |
88 | ## count\_chunks
89 | Count all data chunks in the store.
90 |
91 | ```python
92 | def count_chunks(self):
93 | ...
94 | ```
95 |
96 | ### Value to return
97 | Returns the number of chunks
98 |
99 | Back to top
100 |
101 | ## count\_records
102 | Count all records in the store.
103 |
104 | ```python
105 | def count_records(self):
106 | ...
107 | ```
108 |
109 | ### Value to return
110 | Returns the number of records
111 |
112 | Back to top
113 |
114 | ## delete\_all
115 | Delete all records in the store
116 |
117 | ```python
118 | def delete_all(self):
119 | ...
120 | ```
121 |
122 | Back to top
123 |
124 | ## is\_empty
125 | Tells whether the store is empty or not
126 |
127 | ```python
128 | def is_empty(self):
129 | ...
130 | ```
131 |
132 | ### Value to return
133 | Return a boolean.
134 |
135 | Back to top
136 |
137 | ## latest
138 | Retrieve the datetime of the latest write operation.
139 |
140 | ```python
141 | def latest(self):
142 | ...
143 | ```
144 |
145 | ### Value to return
146 | Return a datetime string
147 |
148 | Back to top
149 |
150 | ## now
151 | Get the current datetime.
152 |
153 | ```python
154 | @staticmethod
155 | def now():
156 | ...
157 | ```
158 |
159 | ### Value to return
160 | Return a datetime string.
161 |
162 | Back to top
163 |
164 | ## now\_dt
165 | Get the current datetime.
166 |
167 | ```python
168 | @staticmethod
169 | def now_dt():
170 | ...
171 | ```
172 |
173 | ### Value to return
174 | Return a datetime object.
175 |
176 | Back to top
177 |
178 | ## read\_transaction
179 | Context manager for executing a Read transaction.
180 |
181 | ```python
182 | def read_transaction(self):
183 | ...
184 | ```
185 |
186 | ### Value to yield
187 | Yields a `litedbc.Cursor` object
188 |
189 | Back to top
190 |
191 | ## transaction
192 | Context manager for executing a transaction.
193 |
194 | ```python
195 | def transaction(self, transaction_mode=):
196 | ...
197 | ```
198 |
199 | | Parameter | Description |
200 | | --- | --- |
201 | | transaction | Instance of `litedbc.TransactionMode` |
202 |
203 | Back to top
204 |
205 | ## write\_transaction
206 | Context manager for executing a Write transaction.
207 |
208 | ```python
209 | def write_transaction(self):
210 | ...
211 | ```
212 |
213 | ### Value to yield
214 | Yields a `litedbc.Cursor` object
215 |
216 | Back to top
217 |
218 | ## \_delete\_record
219 | No docstring
220 |
221 | ```python
222 | def _delete_record(self, record_id):
223 | ...
224 | ```
225 |
226 | Back to top
227 |
228 | ## \_retrieve\_data
229 | No docstring
230 |
231 | ```python
232 | def _retrieve_data(self, record_id, datatype):
233 | ...
234 | ```
235 |
236 | Back to top
237 |
238 | ## \_store\_data
239 | No docstring
240 |
241 | ```python
242 | def _store_data(self, record_id, datatype, value):
243 | ...
244 | ```
245 |
246 | Back to top
247 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/depot/README.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | Module | [Source](/src/jinbase/store/depot.py)
3 |
4 | # Module Overview
5 | > Module: **jinbase.store.depot**
6 |
7 | The Depot store is defined in this module.
8 |
9 | ## Classes
10 | - [**Depot**](/docs/api/modules/jinbase/store/depot/class-Depot.md): This class represents the Depot store. Note that a Depot object isn't intended to be directly instantiated by the user.
11 | - [\_abc\_impl](/docs/api/modules/jinbase/store/depot/class-Depot.md#fields-table) = `<_abc._abc_data object at 0x7eb5e3637440>`
12 | - [chunk\_size](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
13 | - [dbc](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
14 | - [filename](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
15 | - [in\_memory](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
16 | - [is\_closed](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
17 | - [is\_new](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
18 | - [is\_readonly](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
19 | - [jinbase](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
20 | - [model](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
21 | - [timeout](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
22 | - [type\_ref](/docs/api/modules/jinbase/store/depot/class-Depot.md#properties-table); _getter_
23 | - [append](/docs/api/modules/jinbase/store/depot/class-Depot.md#append): No docstring.
24 | - [count\_bytes](/docs/api/modules/jinbase/store/depot/class-Depot.md#count_bytes): Count all data bytes in the store.
25 | - [count\_chunks](/docs/api/modules/jinbase/store/depot/class-Depot.md#count_chunks): Count all data chunks in the store.
26 | - [count\_records](/docs/api/modules/jinbase/store/depot/class-Depot.md#count_records): Count all records in the store.
27 | - [delete](/docs/api/modules/jinbase/store/depot/class-Depot.md#delete): No docstring.
28 | - [delete\_all](/docs/api/modules/jinbase/store/depot/class-Depot.md#delete_all): Delete all records in the store
29 | - [delete\_many](/docs/api/modules/jinbase/store/depot/class-Depot.md#delete_many): No docstring.
30 | - [exists](/docs/api/modules/jinbase/store/depot/class-Depot.md#exists): No docstring.
31 | - [extend](/docs/api/modules/jinbase/store/depot/class-Depot.md#extend): No docstring.
32 | - [fields](/docs/api/modules/jinbase/store/depot/class-Depot.md#fields): No docstring.
33 | - [get](/docs/api/modules/jinbase/store/depot/class-Depot.md#get): No docstring.
34 | - [get\_first](/docs/api/modules/jinbase/store/depot/class-Depot.md#get_first): No docstring.
35 | - [get\_last](/docs/api/modules/jinbase/store/depot/class-Depot.md#get_last): No docstring.
36 | - [info](/docs/api/modules/jinbase/store/depot/class-Depot.md#info): No docstring.
37 | - [is\_empty](/docs/api/modules/jinbase/store/depot/class-Depot.md#is_empty): Tells whether the store is empty or not
38 | - [iterate](/docs/api/modules/jinbase/store/depot/class-Depot.md#iterate): No docstring.
39 | - [latest](/docs/api/modules/jinbase/store/depot/class-Depot.md#latest): Retrieve the datetime of the latest write operation.
40 | - [load\_field](/docs/api/modules/jinbase/store/depot/class-Depot.md#load_field): No docstring.
41 | - [now](/docs/api/modules/jinbase/store/depot/class-Depot.md#now): Get the current datetime.
42 | - [now\_dt](/docs/api/modules/jinbase/store/depot/class-Depot.md#now_dt): Get the current datetime.
43 | - [open\_blob](/docs/api/modules/jinbase/store/depot/class-Depot.md#open_blob): No docstring.
44 | - [position](/docs/api/modules/jinbase/store/depot/class-Depot.md#position): No docstring.
45 | - [read\_transaction](/docs/api/modules/jinbase/store/depot/class-Depot.md#read_transaction): Context manager for executing a Read transaction.
46 | - [transaction](/docs/api/modules/jinbase/store/depot/class-Depot.md#transaction): Context manager for executing a transaction.
47 | - [uid](/docs/api/modules/jinbase/store/depot/class-Depot.md#uid): No docstring.
48 | - [uids](/docs/api/modules/jinbase/store/depot/class-Depot.md#uids): No docstring.
49 | - [write\_transaction](/docs/api/modules/jinbase/store/depot/class-Depot.md#write_transaction): Context manager for executing a Write transaction.
50 | - [\_delete\_record](/docs/api/modules/jinbase/store/depot/class-Depot.md#_delete_record): No docstring.
51 | - [\_get\_record](/docs/api/modules/jinbase/store/depot/class-Depot.md#_get_record): No docstring.
52 | - [\_get\_record\_by\_position](/docs/api/modules/jinbase/store/depot/class-Depot.md#_get_record_by_position): No docstring.
53 | - [\_retrieve\_data](/docs/api/modules/jinbase/store/depot/class-Depot.md#_retrieve_data): No docstring.
54 | - [\_store\_data](/docs/api/modules/jinbase/store/depot/class-Depot.md#_store_data): No docstring.
55 |
56 | Back to top
57 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/depot/class-Depot.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/store/depot/README.md) | [Source](/src/jinbase/store/depot.py)
3 |
4 | # Class Depot
5 | > Module: [jinbase.store.depot](/docs/api/modules/jinbase/store/depot/README.md)
6 | >
7 | > Class: **Depot**
8 | >
9 | > Inheritance: [jinbase.store.Store](/docs/api/modules/jinbase/store/class-Store.md)
10 |
11 | This class represents the Depot store.
12 | Note that a Depot object isn't intended to be directly
13 | instantiated by the user.
14 |
15 | ## Fields table
16 | Here are fields exposed in the class:
17 |
18 | | Field | Value |
19 | | --- | --- |
20 | | \_abc\_impl | `<_abc._abc_data object at 0x7eb5e3637440>` |
21 |
22 | Back to top
23 |
24 | ## Properties table
25 | Here are properties exposed in the class:
26 |
27 | | Property | Methods | Description |
28 | | --- | --- | --- |
29 | | chunk\_size | _getter_ | No docstring. |
30 | | dbc | _getter_ | No docstring. |
31 | | filename | _getter_ | No docstring. |
32 | | in\_memory | _getter_ | No docstring. |
33 | | is\_closed | _getter_ | No docstring. |
34 | | is\_new | _getter_ | No docstring. |
35 | | is\_readonly | _getter_ | No docstring. |
36 | | jinbase | _getter_ | No docstring. |
37 | | model | _getter_ | No docstring. |
38 | | timeout | _getter_ | No docstring. |
39 | | type\_ref | _getter_ | No docstring. |
40 |
41 | Back to top
42 |
43 | # Methods within class
44 | Here are methods exposed in the class:
45 | - [\_\_init\_\_](#__init__)
46 | - [append](#append)
47 | - [count\_bytes](#count_bytes)
48 | - [count\_chunks](#count_chunks)
49 | - [count\_records](#count_records)
50 | - [delete](#delete)
51 | - [delete\_all](#delete_all)
52 | - [delete\_many](#delete_many)
53 | - [exists](#exists)
54 | - [extend](#extend)
55 | - [fields](#fields)
56 | - [get](#get)
57 | - [get\_first](#get_first)
58 | - [get\_last](#get_last)
59 | - [info](#info)
60 | - [is\_empty](#is_empty)
61 | - [iterate](#iterate)
62 | - [latest](#latest)
63 | - [load\_field](#load_field)
64 | - [now](#now)
65 | - [now\_dt](#now_dt)
66 | - [open\_blob](#open_blob)
67 | - [position](#position)
68 | - [read\_transaction](#read_transaction)
69 | - [transaction](#transaction)
70 | - [uid](#uid)
71 | - [uids](#uids)
72 | - [write\_transaction](#write_transaction)
73 | - [\_delete\_record](#_delete_record)
74 | - [\_get\_record](#_get_record)
75 | - [\_get\_record\_by\_position](#_get_record_by_position)
76 | - [\_retrieve\_data](#_retrieve_data)
77 | - [\_store\_data](#_store_data)
78 |
79 | ## \_\_init\_\_
80 | Init
81 |
82 | ```python
83 | def __init__(self, jinbase):
84 | ...
85 | ```
86 |
87 | | Parameter | Description |
88 | | --- | --- |
89 | | jinbase | Jinbase object |
90 |
91 | Back to top
92 |
93 | ## append
94 | No docstring
95 |
96 | ```python
97 | def append(self, value):
98 | ...
99 | ```
100 |
101 | Back to top
102 |
103 | ## count\_bytes
104 | Count all data bytes in the store.
105 |
106 | ```python
107 | def count_bytes(self, uid=None):
108 | ...
109 | ```
110 |
111 | ### Value to return
112 | Returns the count of data bytes
113 |
114 | Back to top
115 |
116 | ## count\_chunks
117 | Count all data chunks in the store.
118 |
119 | ```python
120 | def count_chunks(self, uid=None):
121 | ...
122 | ```
123 |
124 | ### Value to return
125 | Returns the number of chunks
126 |
127 | Back to top
128 |
129 | ## count\_records
130 | Count all records in the store.
131 |
132 | ```python
133 | def count_records(self):
134 | ...
135 | ```
136 |
137 | ### Value to return
138 | Returns the number of records
139 |
140 | Back to top
141 |
142 | ## delete
143 | No docstring
144 |
145 | ```python
146 | def delete(self, uid):
147 | ...
148 | ```
149 |
150 | Back to top
151 |
152 | ## delete\_all
153 | Delete all records in the store
154 |
155 | ```python
156 | def delete_all(self):
157 | ...
158 | ```
159 |
160 | Back to top
161 |
162 | ## delete\_many
163 | No docstring
164 |
165 | ```python
166 | def delete_many(self, uids):
167 | ...
168 | ```
169 |
170 | Back to top
171 |
172 | ## exists
173 | No docstring
174 |
175 | ```python
176 | def exists(self, uid):
177 | ...
178 | ```
179 |
180 | Back to top
181 |
182 | ## extend
183 | No docstring
184 |
185 | ```python
186 | def extend(self, values):
187 | ...
188 | ```
189 |
190 | Back to top
191 |
192 | ## fields
193 | No docstring
194 |
195 | ```python
196 | def fields(self):
197 | ...
198 | ```
199 |
200 | Back to top
201 |
202 | ## get
203 | No docstring
204 |
205 | ```python
206 | def get(self, uid, default=None):
207 | ...
208 | ```
209 |
210 | Back to top
211 |
212 | ## get\_first
213 | No docstring
214 |
215 | ```python
216 | def get_first(self, default=None):
217 | ...
218 | ```
219 |
220 | Back to top
221 |
222 | ## get\_last
223 | No docstring
224 |
225 | ```python
226 | def get_last(self, default=None):
227 | ...
228 | ```
229 |
230 | Back to top
231 |
232 | ## info
233 | No docstring
234 |
235 | ```python
236 | def info(self, uid):
237 | ...
238 | ```
239 |
240 | Back to top
241 |
242 | ## is\_empty
243 | Tells whether the store is empty or not
244 |
245 | ```python
246 | def is_empty(self):
247 | ...
248 | ```
249 |
250 | ### Value to return
251 | Return a boolean.
252 |
253 | Back to top
254 |
255 | ## iterate
256 | No docstring
257 |
258 | ```python
259 | def iterate(self, *, time_range=None, limit=None, asc=True):
260 | ...
261 | ```
262 |
263 | Back to top
264 |
265 | ## latest
266 | Retrieve the datetime of the latest write operation.
267 |
268 | ```python
269 | def latest(self):
270 | ...
271 | ```
272 |
273 | ### Value to return
274 | Return a datetime string
275 |
276 | Back to top
277 |
278 | ## load\_field
279 | No docstring
280 |
281 | ```python
282 | def load_field(self, uid, field, default=None):
283 | ...
284 | ```
285 |
286 | Back to top
287 |
288 | ## now
289 | Get the current datetime.
290 |
291 | ```python
292 | @staticmethod
293 | def now():
294 | ...
295 | ```
296 |
297 | ### Value to return
298 | Return a datetime string.
299 |
300 | Back to top
301 |
302 | ## now\_dt
303 | Get the current datetime.
304 |
305 | ```python
306 | @staticmethod
307 | def now_dt():
308 | ...
309 | ```
310 |
311 | ### Value to return
312 | Return a datetime object.
313 |
314 | Back to top
315 |
316 | ## open\_blob
317 | No docstring
318 |
319 | ```python
320 | def open_blob(self, uid):
321 | ...
322 | ```
323 |
324 | Back to top
325 |
326 | ## position
327 | No docstring
328 |
329 | ```python
330 | def position(self, uid):
331 | ...
332 | ```
333 |
334 | Back to top
335 |
336 | ## read\_transaction
337 | Context manager for executing a Read transaction.
338 |
339 | ```python
340 | def read_transaction(self):
341 | ...
342 | ```
343 |
344 | ### Value to yield
345 | Yields a `litedbc.Cursor` object
346 |
347 | Back to top
348 |
349 | ## transaction
350 | Context manager for executing a transaction.
351 |
352 | ```python
353 | def transaction(self, transaction_mode=):
354 | ...
355 | ```
356 |
357 | | Parameter | Description |
358 | | --- | --- |
359 | | transaction | Instance of `litedbc.TransactionMode` |
360 |
361 | Back to top
362 |
363 | ## uid
364 | No docstring
365 |
366 | ```python
367 | def uid(self, position):
368 | ...
369 | ```
370 |
371 | Back to top
372 |
373 | ## uids
374 | No docstring
375 |
376 | ```python
377 | def uids(self, *, time_range=None, limit=None, asc=True):
378 | ...
379 | ```
380 |
381 | Back to top
382 |
383 | ## write\_transaction
384 | Context manager for executing a Write transaction.
385 |
386 | ```python
387 | def write_transaction(self):
388 | ...
389 | ```
390 |
391 | ### Value to yield
392 | Yields a `litedbc.Cursor` object
393 |
394 | Back to top
395 |
396 | ## \_delete\_record
397 | No docstring
398 |
399 | ```python
400 | def _delete_record(self, record_id):
401 | ...
402 | ```
403 |
404 | Back to top
405 |
406 | ## \_get\_record
407 | No docstring
408 |
409 | ```python
410 | def _get_record(self, uid):
411 | ...
412 | ```
413 |
414 | Back to top
415 |
416 | ## \_get\_record\_by\_position
417 | No docstring
418 |
419 | ```python
420 | def _get_record_by_position(self, position):
421 | ...
422 | ```
423 |
424 | Back to top
425 |
426 | ## \_retrieve\_data
427 | No docstring
428 |
429 | ```python
430 | def _retrieve_data(self, record_id, datatype):
431 | ...
432 | ```
433 |
434 | Back to top
435 |
436 | ## \_store\_data
437 | No docstring
438 |
439 | ```python
440 | def _store_data(self, record_id, datatype, value):
441 | ...
442 | ```
443 |
444 | Back to top
445 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/kv/README.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | Module | [Source](/src/jinbase/store/kv.py)
3 |
4 | # Module Overview
5 | > Module: **jinbase.store.kv**
6 |
7 | The Kv store is defined in this module.
8 |
9 | ## Classes
10 | - [**Kv**](/docs/api/modules/jinbase/store/kv/class-Kv.md): This class represents the Kv store. Note that a Kv object isn't intended to be directly instantiated by the user.
11 | - [\_abc\_impl](/docs/api/modules/jinbase/store/kv/class-Kv.md#fields-table) = `<_abc._abc_data object at 0x7eb5e3648b80>`
12 | - [chunk\_size](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
13 | - [dbc](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
14 | - [filename](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
15 | - [in\_memory](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
16 | - [is\_closed](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
17 | - [is\_new](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
18 | - [is\_readonly](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
19 | - [jinbase](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
20 | - [model](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
21 | - [timeout](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
22 | - [type\_ref](/docs/api/modules/jinbase/store/kv/class-Kv.md#properties-table); _getter_
23 | - [count\_bytes](/docs/api/modules/jinbase/store/kv/class-Kv.md#count_bytes): Count all data bytes in the store.
24 | - [count\_chunks](/docs/api/modules/jinbase/store/kv/class-Kv.md#count_chunks): Count all data chunks in the store.
25 | - [count\_records](/docs/api/modules/jinbase/store/kv/class-Kv.md#count_records): Count all records in the store.
26 | - [delete](/docs/api/modules/jinbase/store/kv/class-Kv.md#delete): No docstring.
27 | - [delete\_all](/docs/api/modules/jinbase/store/kv/class-Kv.md#delete_all): Delete all records in the store
28 | - [delete\_many](/docs/api/modules/jinbase/store/kv/class-Kv.md#delete_many): No docstring.
29 | - [exists](/docs/api/modules/jinbase/store/kv/class-Kv.md#exists): No docstring.
30 | - [fields](/docs/api/modules/jinbase/store/kv/class-Kv.md#fields): No docstring.
31 | - [get](/docs/api/modules/jinbase/store/kv/class-Kv.md#get): No docstring.
32 | - [info](/docs/api/modules/jinbase/store/kv/class-Kv.md#info): No docstring.
33 | - [int\_keys](/docs/api/modules/jinbase/store/kv/class-Kv.md#int_keys): No docstring.
34 | - [is\_empty](/docs/api/modules/jinbase/store/kv/class-Kv.md#is_empty): Tells whether the store is empty or not
35 | - [iterate](/docs/api/modules/jinbase/store/kv/class-Kv.md#iterate): No docstring.
36 | - [key](/docs/api/modules/jinbase/store/kv/class-Kv.md#key): No docstring.
37 | - [keys](/docs/api/modules/jinbase/store/kv/class-Kv.md#keys): No docstring.
38 | - [latest](/docs/api/modules/jinbase/store/kv/class-Kv.md#latest): Retrieve the datetime of the latest write operation.
39 | - [load\_field](/docs/api/modules/jinbase/store/kv/class-Kv.md#load_field): No docstring.
40 | - [now](/docs/api/modules/jinbase/store/kv/class-Kv.md#now): Get the current datetime.
41 | - [now\_dt](/docs/api/modules/jinbase/store/kv/class-Kv.md#now_dt): Get the current datetime.
42 | - [open\_blob](/docs/api/modules/jinbase/store/kv/class-Kv.md#open_blob): No docstring.
43 | - [read\_transaction](/docs/api/modules/jinbase/store/kv/class-Kv.md#read_transaction): Context manager for executing a Read transaction.
44 | - [replace](/docs/api/modules/jinbase/store/kv/class-Kv.md#replace): No docstring.
45 | - [set](/docs/api/modules/jinbase/store/kv/class-Kv.md#set): No docstring.
46 | - [str\_keys](/docs/api/modules/jinbase/store/kv/class-Kv.md#str_keys): No docstring.
47 | - [transaction](/docs/api/modules/jinbase/store/kv/class-Kv.md#transaction): Context manager for executing a transaction.
48 | - [uid](/docs/api/modules/jinbase/store/kv/class-Kv.md#uid): No docstring.
49 | - [update](/docs/api/modules/jinbase/store/kv/class-Kv.md#update): data is a dictionary
50 | - [write\_transaction](/docs/api/modules/jinbase/store/kv/class-Kv.md#write_transaction): Context manager for executing a Write transaction.
51 | - [\_delete\_record](/docs/api/modules/jinbase/store/kv/class-Kv.md#_delete_record): No docstring.
52 | - [\_get\_record\_by\_key](/docs/api/modules/jinbase/store/kv/class-Kv.md#_get_record_by_key): No docstring.
53 | - [\_retrieve\_data](/docs/api/modules/jinbase/store/kv/class-Kv.md#_retrieve_data): No docstring.
54 | - [\_store\_data](/docs/api/modules/jinbase/store/kv/class-Kv.md#_store_data): No docstring.
55 |
56 | Back to top
57 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/kv/class-Kv.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/store/kv/README.md) | [Source](/src/jinbase/store/kv.py)
3 |
4 | # Class Kv
5 | > Module: [jinbase.store.kv](/docs/api/modules/jinbase/store/kv/README.md)
6 | >
7 | > Class: **Kv**
8 | >
9 | > Inheritance: [jinbase.store.Store](/docs/api/modules/jinbase/store/class-Store.md)
10 |
11 | This class represents the Kv store.
12 | Note that a Kv object isn't intended to be directly
13 | instantiated by the user.
14 |
15 | ## Fields table
16 | Here are fields exposed in the class:
17 |
18 | | Field | Value |
19 | | --- | --- |
20 | | \_abc\_impl | `<_abc._abc_data object at 0x7eb5e3648b80>` |
21 |
22 | Back to top
23 |
24 | ## Properties table
25 | Here are properties exposed in the class:
26 |
27 | | Property | Methods | Description |
28 | | --- | --- | --- |
29 | | chunk\_size | _getter_ | No docstring. |
30 | | dbc | _getter_ | No docstring. |
31 | | filename | _getter_ | No docstring. |
32 | | in\_memory | _getter_ | No docstring. |
33 | | is\_closed | _getter_ | No docstring. |
34 | | is\_new | _getter_ | No docstring. |
35 | | is\_readonly | _getter_ | No docstring. |
36 | | jinbase | _getter_ | No docstring. |
37 | | model | _getter_ | No docstring. |
38 | | timeout | _getter_ | No docstring. |
39 | | type\_ref | _getter_ | No docstring. |
40 |
41 | Back to top
42 |
43 | # Methods within class
44 | Here are methods exposed in the class:
45 | - [\_\_init\_\_](#__init__)
46 | - [count\_bytes](#count_bytes)
47 | - [count\_chunks](#count_chunks)
48 | - [count\_records](#count_records)
49 | - [delete](#delete)
50 | - [delete\_all](#delete_all)
51 | - [delete\_many](#delete_many)
52 | - [exists](#exists)
53 | - [fields](#fields)
54 | - [get](#get)
55 | - [info](#info)
56 | - [int\_keys](#int_keys)
57 | - [is\_empty](#is_empty)
58 | - [iterate](#iterate)
59 | - [key](#key)
60 | - [keys](#keys)
61 | - [latest](#latest)
62 | - [load\_field](#load_field)
63 | - [now](#now)
64 | - [now\_dt](#now_dt)
65 | - [open\_blob](#open_blob)
66 | - [read\_transaction](#read_transaction)
67 | - [replace](#replace)
68 | - [set](#set)
69 | - [str\_keys](#str_keys)
70 | - [transaction](#transaction)
71 | - [uid](#uid)
72 | - [update](#update)
73 | - [write\_transaction](#write_transaction)
74 | - [\_delete\_record](#_delete_record)
75 | - [\_get\_record\_by\_key](#_get_record_by_key)
76 | - [\_retrieve\_data](#_retrieve_data)
77 | - [\_store\_data](#_store_data)
78 |
79 | ## \_\_init\_\_
80 | Init
81 |
82 | ```python
83 | def __init__(self, jinbase):
84 | ...
85 | ```
86 |
87 | | Parameter | Description |
88 | | --- | --- |
89 | | jinbase | Jinbase object |
90 |
91 | Back to top
92 |
93 | ## count\_bytes
94 | Count all data bytes in the store.
95 |
96 | ```python
97 | def count_bytes(self, key=None):
98 | ...
99 | ```
100 |
101 | ### Value to return
102 | Returns the count of data bytes
103 |
104 | Back to top
105 |
106 | ## count\_chunks
107 | Count all data chunks in the store.
108 |
109 | ```python
110 | def count_chunks(self, key=None):
111 | ...
112 | ```
113 |
114 | ### Value to return
115 | Returns the number of chunks
116 |
117 | Back to top
118 |
119 | ## count\_records
120 | Count all records in the store.
121 |
122 | ```python
123 | def count_records(self):
124 | ...
125 | ```
126 |
127 | ### Value to return
128 | Returns the number of records
129 |
130 | Back to top
131 |
132 | ## delete
133 | No docstring
134 |
135 | ```python
136 | def delete(self, key):
137 | ...
138 | ```
139 |
140 | Back to top
141 |
142 | ## delete\_all
143 | Delete all records in the store
144 |
145 | ```python
146 | def delete_all(self):
147 | ...
148 | ```
149 |
150 | Back to top
151 |
152 | ## delete\_many
153 | No docstring
154 |
155 | ```python
156 | def delete_many(self, keys):
157 | ...
158 | ```
159 |
160 | Back to top
161 |
162 | ## exists
163 | No docstring
164 |
165 | ```python
166 | def exists(self, key):
167 | ...
168 | ```
169 |
170 | Back to top
171 |
172 | ## fields
173 | No docstring
174 |
175 | ```python
176 | def fields(self):
177 | ...
178 | ```
179 |
180 | Back to top
181 |
182 | ## get
183 | No docstring
184 |
185 | ```python
186 | def get(self, key, default=None):
187 | ...
188 | ```
189 |
190 | Back to top
191 |
192 | ## info
193 | No docstring
194 |
195 | ```python
196 | def info(self, key):
197 | ...
198 | ```
199 |
200 | Back to top
201 |
202 | ## int\_keys
203 | No docstring
204 |
205 | ```python
206 | def int_keys(self, first=None, last=None, *, time_range=None, limit=None, asc=True):
207 | ...
208 | ```
209 |
210 | Back to top
211 |
212 | ## is\_empty
213 | Tells whether the store is empty or not
214 |
215 | ```python
216 | def is_empty(self):
217 | ...
218 | ```
219 |
220 | ### Value to return
221 | Return a boolean.
222 |
223 | Back to top
224 |
225 | ## iterate
226 | No docstring
227 |
228 | ```python
229 | def iterate(self, *, time_range=None, limit=None, asc=True):
230 | ...
231 | ```
232 |
233 | Back to top
234 |
235 | ## key
236 | No docstring
237 |
238 | ```python
239 | def key(self, uid):
240 | ...
241 | ```
242 |
243 | Back to top
244 |
245 | ## keys
246 | No docstring
247 |
248 | ```python
249 | def keys(self, *, time_range=None, limit=None, asc=True):
250 | ...
251 | ```
252 |
253 | Back to top
254 |
255 | ## latest
256 | Retrieve the datetime of the latest write operation.
257 |
258 | ```python
259 | def latest(self):
260 | ...
261 | ```
262 |
263 | ### Value to return
264 | Return a datetime string
265 |
266 | Back to top
267 |
268 | ## load\_field
269 | No docstring
270 |
271 | ```python
272 | def load_field(self, key, field, default=None):
273 | ...
274 | ```
275 |
276 | Back to top
277 |
278 | ## now
279 | Get the current datetime.
280 |
281 | ```python
282 | @staticmethod
283 | def now():
284 | ...
285 | ```
286 |
287 | ### Value to return
288 | Return a datetime string.
289 |
290 | Back to top
291 |
292 | ## now\_dt
293 | Get the current datetime.
294 |
295 | ```python
296 | @staticmethod
297 | def now_dt():
298 | ...
299 | ```
300 |
301 | ### Value to return
302 | Return a datetime object.
303 |
304 | Back to top
305 |
306 | ## open\_blob
307 | No docstring
308 |
309 | ```python
310 | def open_blob(self, key):
311 | ...
312 | ```
313 |
314 | Back to top
315 |
316 | ## read\_transaction
317 | Context manager for executing a Read transaction.
318 |
319 | ```python
320 | def read_transaction(self):
321 | ...
322 | ```
323 |
324 | ### Value to yield
325 | Yields a `litedbc.Cursor` object
326 |
327 | Back to top
328 |
329 | ## replace
330 | No docstring
331 |
332 | ```python
333 | def replace(self, key, value):
334 | ...
335 | ```
336 |
337 | Back to top
338 |
339 | ## set
340 | No docstring
341 |
342 | ```python
343 | def set(self, key, value):
344 | ...
345 | ```
346 |
347 | Back to top
348 |
349 | ## str\_keys
350 | No docstring
351 |
352 | ```python
353 | def str_keys(self, glob=None, *, time_range=None, limit=None, asc=True):
354 | ...
355 | ```
356 |
357 | Back to top
358 |
359 | ## transaction
360 | Context manager for executing a transaction.
361 |
362 | ```python
363 | def transaction(self, transaction_mode=):
364 | ...
365 | ```
366 |
367 | | Parameter | Description |
368 | | --- | --- |
369 | | transaction | Instance of `litedbc.TransactionMode` |
370 |
371 | Back to top
372 |
373 | ## uid
374 | No docstring
375 |
376 | ```python
377 | def uid(self, key):
378 | ...
379 | ```
380 |
381 | Back to top
382 |
383 | ## update
384 | data is a dictionary
385 |
386 | ```python
387 | def update(self, dict_data):
388 | ...
389 | ```
390 |
391 | Back to top
392 |
393 | ## write\_transaction
394 | Context manager for executing a Write transaction.
395 |
396 | ```python
397 | def write_transaction(self):
398 | ...
399 | ```
400 |
401 | ### Value to yield
402 | Yields a `litedbc.Cursor` object
403 |
404 | Back to top
405 |
406 | ## \_delete\_record
407 | No docstring
408 |
409 | ```python
410 | def _delete_record(self, record_id):
411 | ...
412 | ```
413 |
414 | Back to top
415 |
416 | ## \_get\_record\_by\_key
417 | No docstring
418 |
419 | ```python
420 | def _get_record_by_key(self, key):
421 | ...
422 | ```
423 |
424 | Back to top
425 |
426 | ## \_retrieve\_data
427 | No docstring
428 |
429 | ```python
430 | def _retrieve_data(self, record_id, datatype):
431 | ...
432 | ```
433 |
434 | Back to top
435 |
436 | ## \_store\_data
437 | No docstring
438 |
439 | ```python
440 | def _store_data(self, record_id, datatype, value):
441 | ...
442 | ```
443 |
444 | Back to top
445 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/queue/README.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | Module | [Source](/src/jinbase/store/queue.py)
3 |
4 | # Module Overview
5 | > Module: **jinbase.store.queue**
6 |
7 | The Queue store is defined in this module.
8 |
9 | ## Classes
10 | - [**Queue**](/docs/api/modules/jinbase/store/queue/class-Queue.md): This class represents the Queue store. Note that a Queue object isn't intended to be directly instantiated by the user.
11 | - [\_abc\_impl](/docs/api/modules/jinbase/store/queue/class-Queue.md#fields-table) = `<_abc._abc_data object at 0x7eb5e36495c0>`
12 | - [chunk\_size](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
13 | - [dbc](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
14 | - [filename](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
15 | - [in\_memory](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
16 | - [is\_closed](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
17 | - [is\_new](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
18 | - [is\_readonly](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
19 | - [jinbase](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
20 | - [model](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
21 | - [timeout](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
22 | - [type\_ref](/docs/api/modules/jinbase/store/queue/class-Queue.md#properties-table); _getter_
23 | - [back\_uid](/docs/api/modules/jinbase/store/queue/class-Queue.md#back_uid): No docstring.
24 | - [count\_back\_bytes](/docs/api/modules/jinbase/store/queue/class-Queue.md#count_back_bytes): No docstring.
25 | - [count\_back\_chunks](/docs/api/modules/jinbase/store/queue/class-Queue.md#count_back_chunks): No docstring.
26 | - [count\_bytes](/docs/api/modules/jinbase/store/queue/class-Queue.md#count_bytes): Count all data bytes in the store.
27 | - [count\_chunks](/docs/api/modules/jinbase/store/queue/class-Queue.md#count_chunks): Count all data chunks in the store.
28 | - [count\_front\_bytes](/docs/api/modules/jinbase/store/queue/class-Queue.md#count_front_bytes): No docstring.
29 | - [count\_front\_chunks](/docs/api/modules/jinbase/store/queue/class-Queue.md#count_front_chunks): No docstring.
30 | - [count\_records](/docs/api/modules/jinbase/store/queue/class-Queue.md#count_records): Count all records in the store.
31 | - [delete\_all](/docs/api/modules/jinbase/store/queue/class-Queue.md#delete_all): Delete all records in the store
32 | - [dequeue](/docs/api/modules/jinbase/store/queue/class-Queue.md#dequeue): No docstring.
33 | - [enqueue](/docs/api/modules/jinbase/store/queue/class-Queue.md#enqueue): No docstring.
34 | - [enqueue\_many](/docs/api/modules/jinbase/store/queue/class-Queue.md#enqueue_many): No docstring.
35 | - [front\_uid](/docs/api/modules/jinbase/store/queue/class-Queue.md#front_uid): No docstring.
36 | - [info\_back](/docs/api/modules/jinbase/store/queue/class-Queue.md#info_back): No docstring.
37 | - [info\_front](/docs/api/modules/jinbase/store/queue/class-Queue.md#info_front): No docstring.
38 | - [is\_empty](/docs/api/modules/jinbase/store/queue/class-Queue.md#is_empty): Tells whether the store is empty or not
39 | - [latest](/docs/api/modules/jinbase/store/queue/class-Queue.md#latest): Retrieve the datetime of the latest write operation.
40 | - [now](/docs/api/modules/jinbase/store/queue/class-Queue.md#now): Get the current datetime.
41 | - [now\_dt](/docs/api/modules/jinbase/store/queue/class-Queue.md#now_dt): Get the current datetime.
42 | - [peek\_back](/docs/api/modules/jinbase/store/queue/class-Queue.md#peek_back): No docstring.
43 | - [peek\_front](/docs/api/modules/jinbase/store/queue/class-Queue.md#peek_front): No docstring.
44 | - [read\_transaction](/docs/api/modules/jinbase/store/queue/class-Queue.md#read_transaction): Context manager for executing a Read transaction.
45 | - [transaction](/docs/api/modules/jinbase/store/queue/class-Queue.md#transaction): Context manager for executing a transaction.
46 | - [write\_transaction](/docs/api/modules/jinbase/store/queue/class-Queue.md#write_transaction): Context manager for executing a Write transaction.
47 | - [\_delete\_record](/docs/api/modules/jinbase/store/queue/class-Queue.md#_delete_record): No docstring.
48 | - [\_get\_back](/docs/api/modules/jinbase/store/queue/class-Queue.md#_get_back): No docstring.
49 | - [\_get\_front](/docs/api/modules/jinbase/store/queue/class-Queue.md#_get_front): No docstring.
50 | - [\_retrieve\_data](/docs/api/modules/jinbase/store/queue/class-Queue.md#_retrieve_data): No docstring.
51 | - [\_store\_data](/docs/api/modules/jinbase/store/queue/class-Queue.md#_store_data): No docstring.
52 |
53 | Back to top
54 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/queue/class-Queue.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/store/queue/README.md) | [Source](/src/jinbase/store/queue.py)
3 |
4 | # Class Queue
5 | > Module: [jinbase.store.queue](/docs/api/modules/jinbase/store/queue/README.md)
6 | >
7 | > Class: **Queue**
8 | >
9 | > Inheritance: [jinbase.store.Store](/docs/api/modules/jinbase/store/class-Store.md)
10 |
11 | This class represents the Queue store.
12 | Note that a Queue object isn't intended to be directly
13 | instantiated by the user.
14 |
15 | ## Fields table
16 | Here are fields exposed in the class:
17 |
18 | | Field | Value |
19 | | --- | --- |
20 | | \_abc\_impl | `<_abc._abc_data object at 0x7eb5e36495c0>` |
21 |
22 | Back to top
23 |
24 | ## Properties table
25 | Here are properties exposed in the class:
26 |
27 | | Property | Methods | Description |
28 | | --- | --- | --- |
29 | | chunk\_size | _getter_ | No docstring. |
30 | | dbc | _getter_ | No docstring. |
31 | | filename | _getter_ | No docstring. |
32 | | in\_memory | _getter_ | No docstring. |
33 | | is\_closed | _getter_ | No docstring. |
34 | | is\_new | _getter_ | No docstring. |
35 | | is\_readonly | _getter_ | No docstring. |
36 | | jinbase | _getter_ | No docstring. |
37 | | model | _getter_ | No docstring. |
38 | | timeout | _getter_ | No docstring. |
39 | | type\_ref | _getter_ | No docstring. |
40 |
41 | Back to top
42 |
43 | # Methods within class
44 | Here are methods exposed in the class:
45 | - [\_\_init\_\_](#__init__)
46 | - [back\_uid](#back_uid)
47 | - [count\_back\_bytes](#count_back_bytes)
48 | - [count\_back\_chunks](#count_back_chunks)
49 | - [count\_bytes](#count_bytes)
50 | - [count\_chunks](#count_chunks)
51 | - [count\_front\_bytes](#count_front_bytes)
52 | - [count\_front\_chunks](#count_front_chunks)
53 | - [count\_records](#count_records)
54 | - [delete\_all](#delete_all)
55 | - [dequeue](#dequeue)
56 | - [enqueue](#enqueue)
57 | - [enqueue\_many](#enqueue_many)
58 | - [front\_uid](#front_uid)
59 | - [info\_back](#info_back)
60 | - [info\_front](#info_front)
61 | - [is\_empty](#is_empty)
62 | - [latest](#latest)
63 | - [now](#now)
64 | - [now\_dt](#now_dt)
65 | - [peek\_back](#peek_back)
66 | - [peek\_front](#peek_front)
67 | - [read\_transaction](#read_transaction)
68 | - [transaction](#transaction)
69 | - [write\_transaction](#write_transaction)
70 | - [\_delete\_record](#_delete_record)
71 | - [\_get\_back](#_get_back)
72 | - [\_get\_front](#_get_front)
73 | - [\_retrieve\_data](#_retrieve_data)
74 | - [\_store\_data](#_store_data)
75 |
76 | ## \_\_init\_\_
77 | Init
78 |
79 | ```python
80 | def __init__(self, jinbase):
81 | ...
82 | ```
83 |
84 | | Parameter | Description |
85 | | --- | --- |
86 | | jinbase | Jinbase object |
87 |
88 | Back to top
89 |
90 | ## back\_uid
91 | No docstring
92 |
93 | ```python
94 | def back_uid(self):
95 | ...
96 | ```
97 |
98 | Back to top
99 |
100 | ## count\_back\_bytes
101 | No docstring
102 |
103 | ```python
104 | def count_back_bytes(self):
105 | ...
106 | ```
107 |
108 | Back to top
109 |
110 | ## count\_back\_chunks
111 | No docstring
112 |
113 | ```python
114 | def count_back_chunks(self):
115 | ...
116 | ```
117 |
118 | Back to top
119 |
120 | ## count\_bytes
121 | Count all data bytes in the store.
122 |
123 | ```python
124 | def count_bytes(self):
125 | ...
126 | ```
127 |
128 | ### Value to return
129 | Returns the count of data bytes
130 |
131 | Back to top
132 |
133 | ## count\_chunks
134 | Count all data chunks in the store.
135 |
136 | ```python
137 | def count_chunks(self):
138 | ...
139 | ```
140 |
141 | ### Value to return
142 | Returns the number of chunks
143 |
144 | Back to top
145 |
146 | ## count\_front\_bytes
147 | No docstring
148 |
149 | ```python
150 | def count_front_bytes(self):
151 | ...
152 | ```
153 |
154 | Back to top
155 |
156 | ## count\_front\_chunks
157 | No docstring
158 |
159 | ```python
160 | def count_front_chunks(self):
161 | ...
162 | ```
163 |
164 | Back to top
165 |
166 | ## count\_records
167 | Count all records in the store.
168 |
169 | ```python
170 | def count_records(self):
171 | ...
172 | ```
173 |
174 | ### Value to return
175 | Returns the number of records
176 |
177 | Back to top
178 |
179 | ## delete\_all
180 | Delete all records in the store
181 |
182 | ```python
183 | def delete_all(self):
184 | ...
185 | ```
186 |
187 | Back to top
188 |
189 | ## dequeue
190 | No docstring
191 |
192 | ```python
193 | def dequeue(self, default=None):
194 | ...
195 | ```
196 |
197 | Back to top
198 |
199 | ## enqueue
200 | No docstring
201 |
202 | ```python
203 | def enqueue(self, value):
204 | ...
205 | ```
206 |
207 | Back to top
208 |
209 | ## enqueue\_many
210 | No docstring
211 |
212 | ```python
213 | def enqueue_many(self, values):
214 | ...
215 | ```
216 |
217 | Back to top
218 |
219 | ## front\_uid
220 | No docstring
221 |
222 | ```python
223 | def front_uid(self):
224 | ...
225 | ```
226 |
227 | Back to top
228 |
229 | ## info\_back
230 | No docstring
231 |
232 | ```python
233 | def info_back(self):
234 | ...
235 | ```
236 |
237 | Back to top
238 |
239 | ## info\_front
240 | No docstring
241 |
242 | ```python
243 | def info_front(self):
244 | ...
245 | ```
246 |
247 | Back to top
248 |
249 | ## is\_empty
250 | Tells whether the store is empty or not
251 |
252 | ```python
253 | def is_empty(self):
254 | ...
255 | ```
256 |
257 | ### Value to return
258 | Return a boolean.
259 |
260 | Back to top
261 |
262 | ## latest
263 | Retrieve the datetime of the latest write operation.
264 |
265 | ```python
266 | def latest(self):
267 | ...
268 | ```
269 |
270 | ### Value to return
271 | Return a datetime string
272 |
273 | Back to top
274 |
275 | ## now
276 | Get the current datetime.
277 |
278 | ```python
279 | @staticmethod
280 | def now():
281 | ...
282 | ```
283 |
284 | ### Value to return
285 | Return a datetime string.
286 |
287 | Back to top
288 |
289 | ## now\_dt
290 | Get the current datetime.
291 |
292 | ```python
293 | @staticmethod
294 | def now_dt():
295 | ...
296 | ```
297 |
298 | ### Value to return
299 | Return a datetime object.
300 |
301 | Back to top
302 |
303 | ## peek\_back
304 | No docstring
305 |
306 | ```python
307 | def peek_back(self, default=None):
308 | ...
309 | ```
310 |
311 | Back to top
312 |
313 | ## peek\_front
314 | No docstring
315 |
316 | ```python
317 | def peek_front(self, default=None):
318 | ...
319 | ```
320 |
321 | Back to top
322 |
323 | ## read\_transaction
324 | Context manager for executing a Read transaction.
325 |
326 | ```python
327 | def read_transaction(self):
328 | ...
329 | ```
330 |
331 | ### Value to yield
332 | Yields a `litedbc.Cursor` object
333 |
334 | Back to top
335 |
336 | ## transaction
337 | Context manager for executing a transaction.
338 |
339 | ```python
340 | def transaction(self, transaction_mode=):
341 | ...
342 | ```
343 |
344 | | Parameter | Description |
345 | | --- | --- |
346 | | transaction | Instance of `litedbc.TransactionMode` |
347 |
348 | Back to top
349 |
350 | ## write\_transaction
351 | Context manager for executing a Write transaction.
352 |
353 | ```python
354 | def write_transaction(self):
355 | ...
356 | ```
357 |
358 | ### Value to yield
359 | Yields a `litedbc.Cursor` object
360 |
361 | Back to top
362 |
363 | ## \_delete\_record
364 | No docstring
365 |
366 | ```python
367 | def _delete_record(self, record_id):
368 | ...
369 | ```
370 |
371 | Back to top
372 |
373 | ## \_get\_back
374 | No docstring
375 |
376 | ```python
377 | def _get_back(self):
378 | ...
379 | ```
380 |
381 | Back to top
382 |
383 | ## \_get\_front
384 | No docstring
385 |
386 | ```python
387 | def _get_front(self):
388 | ...
389 | ```
390 |
391 | Back to top
392 |
393 | ## \_retrieve\_data
394 | No docstring
395 |
396 | ```python
397 | def _retrieve_data(self, record_id, datatype):
398 | ...
399 | ```
400 |
401 | Back to top
402 |
403 | ## \_store\_data
404 | No docstring
405 |
406 | ```python
407 | def _store_data(self, record_id, datatype, value):
408 | ...
409 | ```
410 |
411 | Back to top
412 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/stack/README.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | Module | [Source](/src/jinbase/store/stack.py)
3 |
4 | # Module Overview
5 | > Module: **jinbase.store.stack**
6 |
7 | The Stack store is defined in this module.
8 |
9 | ## Classes
10 | - [**Stack**](/docs/api/modules/jinbase/store/stack/class-Stack.md): This class represents the Stack store. Note that a Stack object isn't intended to be directly instantiated by the user.
11 | - [\_abc\_impl](/docs/api/modules/jinbase/store/stack/class-Stack.md#fields-table) = `<_abc._abc_data object at 0x7eb5e3649cc0>`
12 | - [chunk\_size](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
13 | - [dbc](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
14 | - [filename](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
15 | - [in\_memory](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
16 | - [is\_closed](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
17 | - [is\_new](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
18 | - [is\_readonly](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
19 | - [jinbase](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
20 | - [model](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
21 | - [timeout](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
22 | - [type\_ref](/docs/api/modules/jinbase/store/stack/class-Stack.md#properties-table); _getter_
23 | - [count\_bytes](/docs/api/modules/jinbase/store/stack/class-Stack.md#count_bytes): Count all data bytes in the store.
24 | - [count\_chunks](/docs/api/modules/jinbase/store/stack/class-Stack.md#count_chunks): Count all data chunks in the store.
25 | - [count\_records](/docs/api/modules/jinbase/store/stack/class-Stack.md#count_records): Count all records in the store.
26 | - [count\_top\_bytes](/docs/api/modules/jinbase/store/stack/class-Stack.md#count_top_bytes): No docstring.
27 | - [count\_top\_chunks](/docs/api/modules/jinbase/store/stack/class-Stack.md#count_top_chunks): No docstring.
28 | - [delete\_all](/docs/api/modules/jinbase/store/stack/class-Stack.md#delete_all): Delete all records in the store
29 | - [info\_top](/docs/api/modules/jinbase/store/stack/class-Stack.md#info_top): No docstring.
30 | - [is\_empty](/docs/api/modules/jinbase/store/stack/class-Stack.md#is_empty): Tells whether the store is empty or not
31 | - [latest](/docs/api/modules/jinbase/store/stack/class-Stack.md#latest): Retrieve the datetime of the latest write operation.
32 | - [now](/docs/api/modules/jinbase/store/stack/class-Stack.md#now): Get the current datetime.
33 | - [now\_dt](/docs/api/modules/jinbase/store/stack/class-Stack.md#now_dt): Get the current datetime.
34 | - [peek](/docs/api/modules/jinbase/store/stack/class-Stack.md#peek): No docstring.
35 | - [pop](/docs/api/modules/jinbase/store/stack/class-Stack.md#pop): No docstring.
36 | - [push](/docs/api/modules/jinbase/store/stack/class-Stack.md#push): No docstring.
37 | - [push\_many](/docs/api/modules/jinbase/store/stack/class-Stack.md#push_many): No docstring.
38 | - [read\_transaction](/docs/api/modules/jinbase/store/stack/class-Stack.md#read_transaction): Context manager for executing a Read transaction.
39 | - [top\_uid](/docs/api/modules/jinbase/store/stack/class-Stack.md#top_uid): No docstring.
40 | - [transaction](/docs/api/modules/jinbase/store/stack/class-Stack.md#transaction): Context manager for executing a transaction.
41 | - [write\_transaction](/docs/api/modules/jinbase/store/stack/class-Stack.md#write_transaction): Context manager for executing a Write transaction.
42 | - [\_delete\_record](/docs/api/modules/jinbase/store/stack/class-Stack.md#_delete_record): No docstring.
43 | - [\_get\_top](/docs/api/modules/jinbase/store/stack/class-Stack.md#_get_top): No docstring.
44 | - [\_retrieve\_data](/docs/api/modules/jinbase/store/stack/class-Stack.md#_retrieve_data): No docstring.
45 | - [\_store\_data](/docs/api/modules/jinbase/store/stack/class-Stack.md#_store_data): No docstring.
46 |
47 | Back to top
48 |
--------------------------------------------------------------------------------
/docs/api/modules/jinbase/store/stack/class-Stack.md:
--------------------------------------------------------------------------------
1 | ###### Jinbase API Reference
2 | [Home](/docs/api/README.md) | [Project](/README.md) | [Module](/docs/api/modules/jinbase/store/stack/README.md) | [Source](/src/jinbase/store/stack.py)
3 |
4 | # Class Stack
5 | > Module: [jinbase.store.stack](/docs/api/modules/jinbase/store/stack/README.md)
6 | >
7 | > Class: **Stack**
8 | >
9 | > Inheritance: [jinbase.store.Store](/docs/api/modules/jinbase/store/class-Store.md)
10 |
11 | This class represents the Stack store.
12 | Note that a Stack object isn't intended to be directly
13 | instantiated by the user.
14 |
15 | ## Fields table
16 | Here are fields exposed in the class:
17 |
18 | | Field | Value |
19 | | --- | --- |
20 | | \_abc\_impl | `<_abc._abc_data object at 0x7eb5e3649cc0>` |
21 |
22 | Back to top
23 |
24 | ## Properties table
25 | Here are properties exposed in the class:
26 |
27 | | Property | Methods | Description |
28 | | --- | --- | --- |
29 | | chunk\_size | _getter_ | No docstring. |
30 | | dbc | _getter_ | No docstring. |
31 | | filename | _getter_ | No docstring. |
32 | | in\_memory | _getter_ | No docstring. |
33 | | is\_closed | _getter_ | No docstring. |
34 | | is\_new | _getter_ | No docstring. |
35 | | is\_readonly | _getter_ | No docstring. |
36 | | jinbase | _getter_ | No docstring. |
37 | | model | _getter_ | No docstring. |
38 | | timeout | _getter_ | No docstring. |
39 | | type\_ref | _getter_ | No docstring. |
40 |
41 | Back to top
42 |
43 | # Methods within class
44 | Here are methods exposed in the class:
45 | - [\_\_init\_\_](#__init__)
46 | - [count\_bytes](#count_bytes)
47 | - [count\_chunks](#count_chunks)
48 | - [count\_records](#count_records)
49 | - [count\_top\_bytes](#count_top_bytes)
50 | - [count\_top\_chunks](#count_top_chunks)
51 | - [delete\_all](#delete_all)
52 | - [info\_top](#info_top)
53 | - [is\_empty](#is_empty)
54 | - [latest](#latest)
55 | - [now](#now)
56 | - [now\_dt](#now_dt)
57 | - [peek](#peek)
58 | - [pop](#pop)
59 | - [push](#push)
60 | - [push\_many](#push_many)
61 | - [read\_transaction](#read_transaction)
62 | - [top\_uid](#top_uid)
63 | - [transaction](#transaction)
64 | - [write\_transaction](#write_transaction)
65 | - [\_delete\_record](#_delete_record)
66 | - [\_get\_top](#_get_top)
67 | - [\_retrieve\_data](#_retrieve_data)
68 | - [\_store\_data](#_store_data)
69 |
70 | ## \_\_init\_\_
71 | Init
72 |
73 | ```python
74 | def __init__(self, jinbase):
75 | ...
76 | ```
77 |
78 | | Parameter | Description |
79 | | --- | --- |
80 | | jinbase | Jinbase object |
81 |
82 | Back to top
83 |
84 | ## count\_bytes
85 | Count all data bytes in the store.
86 |
87 | ```python
88 | def count_bytes(self):
89 | ...
90 | ```
91 |
92 | ### Value to return
93 | Returns the count of data bytes
94 |
95 | Back to top
96 |
97 | ## count\_chunks
98 | Count all data chunks in the store.
99 |
100 | ```python
101 | def count_chunks(self):
102 | ...
103 | ```
104 |
105 | ### Value to return
106 | Returns the number of chunks
107 |
108 | Back to top
109 |
110 | ## count\_records
111 | Count all records in the store.
112 |
113 | ```python
114 | def count_records(self):
115 | ...
116 | ```
117 |
118 | ### Value to return
119 | Returns the number of records
120 |
121 | Back to top
122 |
123 | ## count\_top\_bytes
124 | No docstring
125 |
126 | ```python
127 | def count_top_bytes(self):
128 | ...
129 | ```
130 |
131 | Back to top
132 |
133 | ## count\_top\_chunks
134 | No docstring
135 |
136 | ```python
137 | def count_top_chunks(self):
138 | ...
139 | ```
140 |
141 | Back to top
142 |
143 | ## delete\_all
144 | Delete all records in the store
145 |
146 | ```python
147 | def delete_all(self):
148 | ...
149 | ```
150 |
151 | Back to top
152 |
153 | ## info\_top
154 | No docstring
155 |
156 | ```python
157 | def info_top(self):
158 | ...
159 | ```
160 |
161 | Back to top
162 |
163 | ## is\_empty
164 | Tells whether the store is empty or not
165 |
166 | ```python
167 | def is_empty(self):
168 | ...
169 | ```
170 |
171 | ### Value to return
172 | Return a boolean.
173 |
174 | Back to top
175 |
176 | ## latest
177 | Retrieve the datetime of the latest write operation.
178 |
179 | ```python
180 | def latest(self):
181 | ...
182 | ```
183 |
184 | ### Value to return
185 | Return a datetime string
186 |
187 | Back to top
188 |
189 | ## now
190 | Get the current datetime.
191 |
192 | ```python
193 | @staticmethod
194 | def now():
195 | ...
196 | ```
197 |
198 | ### Value to return
199 | Return a datetime string.
200 |
201 | Back to top
202 |
203 | ## now\_dt
204 | Get the current datetime.
205 |
206 | ```python
207 | @staticmethod
208 | def now_dt():
209 | ...
210 | ```
211 |
212 | ### Value to return
213 | Return a datetime object.
214 |
215 | Back to top
216 |
217 | ## peek
218 | No docstring
219 |
220 | ```python
221 | def peek(self, default=None):
222 | ...
223 | ```
224 |
225 | Back to top
226 |
227 | ## pop
228 | No docstring
229 |
230 | ```python
231 | def pop(self, default=None):
232 | ...
233 | ```
234 |
235 | Back to top
236 |
237 | ## push
238 | No docstring
239 |
240 | ```python
241 | def push(self, value):
242 | ...
243 | ```
244 |
245 | Back to top
246 |
247 | ## push\_many
248 | No docstring
249 |
250 | ```python
251 | def push_many(self, values):
252 | ...
253 | ```
254 |
255 | Back to top
256 |
257 | ## read\_transaction
258 | Context manager for executing a Read transaction.
259 |
260 | ```python
261 | def read_transaction(self):
262 | ...
263 | ```
264 |
265 | ### Value to yield
266 | Yields a `litedbc.Cursor` object
267 |
268 | Back to top
269 |
270 | ## top\_uid
271 | No docstring
272 |
273 | ```python
274 | def top_uid(self):
275 | ...
276 | ```
277 |
278 | Back to top
279 |
280 | ## transaction
281 | Context manager for executing a transaction.
282 |
283 | ```python
284 | def transaction(self, transaction_mode=):
285 | ...
286 | ```
287 |
288 | | Parameter | Description |
289 | | --- | --- |
290 | | transaction | Instance of `litedbc.TransactionMode` |
291 |
292 | Back to top
293 |
294 | ## write\_transaction
295 | Context manager for executing a Write transaction.
296 |
297 | ```python
298 | def write_transaction(self):
299 | ...
300 | ```
301 |
302 | ### Value to yield
303 | Yields a `litedbc.Cursor` object
304 |
305 | Back to top
306 |
307 | ## \_delete\_record
308 | No docstring
309 |
310 | ```python
311 | def _delete_record(self, record_id):
312 | ...
313 | ```
314 |
315 | Back to top
316 |
317 | ## \_get\_top
318 | No docstring
319 |
320 | ```python
321 | def _get_top(self):
322 | ...
323 | ```
324 |
325 | Back to top
326 |
327 | ## \_retrieve\_data
328 | No docstring
329 |
330 | ```python
331 | def _retrieve_data(self, record_id, datatype):
332 | ...
333 | ```
334 |
335 | Back to top
336 |
337 | ## \_store\_data
338 | No docstring
339 |
340 | ```python
341 | def _store_data(self, record_id, datatype, value):
342 | ...
343 | ```
344 |
345 | Back to top
346 |
--------------------------------------------------------------------------------
/mikedoc.kvf:
--------------------------------------------------------------------------------
1 | # project name
2 | project_name = 'Jinbase'
3 |
4 | # project's website or README
5 | project_url = '/README.md'
6 |
7 | # package directory (relative path)
8 | pkg_dir = 'src/jinbase'
9 |
10 | # API directory (relative path)
11 | api_dir = 'docs/api'
12 |
--------------------------------------------------------------------------------
/pyproject.toml:
--------------------------------------------------------------------------------
1 | # https://stackoverflow.com/q/76248637 (this is why setup.cfg/setup.py are still relevant !)
2 | # https://packaging.python.org/en/latest/guides/writing-pyproject-toml
3 | # https://setuptools.pypa.io/en/latest/userguide/pyproject_config.html
4 | # https://setuptools.pypa.io/en/latest/userguide/datafiles.html
5 |
6 | [build-system]
7 | requires = ["setuptools"]
8 | build-backend = "setuptools.build_meta"
9 |
--------------------------------------------------------------------------------
/setup.cfg:
--------------------------------------------------------------------------------
1 | [metadata]
2 | name = jinbase
3 | version = file: VERSION
4 | url = https://github.com/pyrustic/jinbase
5 | author = Pyrustic Architect
6 | author_email = rusticalex@yahoo.com
7 | maintainer = Pyrustic Architect
8 | maintainer_email = rusticalex@yahoo.com
9 | description = Multi-model transactional embedded database
10 | long_description = file: README.md
11 | long_description_content_type = text/markdown
12 | license = MIT
13 | keywords =
14 | pyrustic
15 | # https://pypi.org/classifiers/
16 | # Development Status :: 3 - Alpha
17 | # Development Status :: 4 - Beta
18 | # Development Status :: 5 - Production/Stable
19 | classifiers =
20 | Programming Language :: Python
21 | Programming Language :: Python :: 3
22 | License :: OSI Approved :: MIT License
23 | Operating System :: OS Independent
24 | Intended Audience :: Developers
25 | Development Status :: 4 - Beta
26 |
27 | [options]
28 | python_requires = >=3.5
29 | package_dir =
30 | = src
31 | packages = find:
32 | include_package_data = true
33 | zip_safe = false
34 | install_requires =
35 | paradict
36 | litedbc
37 |
38 | [options.packages.find]
39 | where = src
40 |
41 | [options.entry_points]
42 | console_scripts =
43 | jinbase = jinbase.__main__:main
44 |
--------------------------------------------------------------------------------
/setup.py:
--------------------------------------------------------------------------------
1 | # File generated by Setupinit
2 | import setuptools
3 |
4 |
5 | if __name__ == "__main__":
6 | setuptools.setup()
7 |
--------------------------------------------------------------------------------
/src/jinbase/__init__.py:
--------------------------------------------------------------------------------
1 | """The main module of Jinbase."""
2 | from datetime import datetime, timezone
3 | from paradict import TypeRef
4 | from litedbc import LiteDBC, TransactionMode
5 | from jinbase import errors, queries, misc, const
6 | from jinbase.store import RecordInfo
7 | from jinbase.store.depot import Depot
8 | from jinbase.store.kv import Kv
9 | from jinbase.store.queue import Queue
10 | from jinbase.store.stack import Stack
11 | from jinbase.const import (Model, TimestampPrecision, TIMESTAMP_PRECISION,
12 | TIMEOUT, CHUNK_SIZE, JINBASE_HOME, JINBASE_VERSION,
13 | USER_HOME, DATETIME_FORMAT)
14 |
15 |
16 | __all__ = ["Jinbase", "Model", "TypeRef", "RecordInfo",
17 | "TimestampPrecision", "TIMEOUT", "CHUNK_SIZE",
18 | "TIMESTAMP_PRECISION", "DATETIME_FORMAT",
19 | "USER_HOME", "JINBASE_HOME", "JINBASE_VERSION"]
20 |
21 |
22 | class Jinbase:
23 | """The Jinbase class. A Jinbase object is intended to
24 | be directly instantiated by the user."""
25 | def __init__(self, filename=None, *, auto_create=True,
26 | is_readonly=False, timeout=TIMEOUT,
27 | type_ref=None, chunk_size=CHUNK_SIZE,
28 | timestamp_precision=TIMESTAMP_PRECISION):
29 | """
30 | Init.
31 |
32 | [params]
33 | - filename: The filename of the Jinbase database.
34 | If the pointed file doesn't exist, it will be created
35 | if `auto_create` is set to True.
36 | - auto_create: Boolean to tell whether a nonexistent database file
37 | should automatically be created or not. Defaults to True.
38 | - is_readonly: Boolean to tell whether the database connection should be in
39 | readonly or not.
40 | - timeout: Timeout in seconds for all database operations.
41 | Defaults to the value of `jinbase.TIMEOUT`
42 | - type_ref: A paradict.TypeRef instance
43 | - chunk_size: Chunk size in bytes. Defaults to `jinbase.CHUNK_SIZE`.
44 | Note that this value is only relevant when the Jinbase tables are created.
45 | - timestamp_precision: An instance of the `jinbase.TimestampPrecision` namedtuple.
46 | Defaults to `jinbase.TIMESTAMP_PRECISION`.
47 | Note that this value is only relevant when the Jinbase tables are created.
48 | """
49 | self._dbc = create_dbc(filename, auto_create, is_readonly, timeout)
50 | with self._dbc.cursor() as cur:
51 | cur.executescript(queries.INIT_SCRIPT)
52 | chunk_size = int(chunk_size) if chunk_size else CHUNK_SIZE
53 | x = ensure_jinbase(self._dbc, chunk_size,
54 | TimestampPrecision(timestamp_precision))
55 | self._version, self._created_at, self._chunk_size, self._timestamp_precision = x
56 | self._creation_dt = datetime.fromisoformat(self._created_at).astimezone(tz=timezone.utc)
57 | self._auto_create = auto_create
58 | self._filename = self._dbc.filename
59 | self._is_readonly = self._dbc.is_readonly
60 | self._timeout = self._dbc.timeout
61 | self._type_ref = TypeRef() if type_ref is None else type_ref
62 | # stores
63 | self._kv = Kv(self)
64 | self._depot = Depot(self)
65 | self._queue = Queue(self)
66 | self._stack = Stack(self)
67 |
68 | @property
69 | def kv(self):
70 | return self._kv
71 |
72 | @property
73 | def depot(self):
74 | return self._depot
75 |
76 | @property
77 | def queue(self):
78 | return self._queue
79 |
80 | @property
81 | def stack(self):
82 | return self._stack
83 |
84 | @property
85 | def filename(self):
86 | return self._filename
87 |
88 | @property
89 | def is_readonly(self):
90 | return self._is_readonly
91 |
92 | @property
93 | def timeout(self):
94 | return self._timeout
95 |
96 | @property
97 | def type_ref(self):
98 | return self._type_ref
99 |
100 | @property
101 | def chunk_size(self):
102 | return self._chunk_size
103 |
104 | @property
105 | def timestamp_precision(self):
106 | return self._timestamp_precision
107 |
108 | @property
109 | def dbc(self):
110 | """The instance of litedbc.LiteDBC"""
111 | return self._dbc
112 |
113 | @property
114 | def created_at(self):
115 | return self._created_at
116 |
117 | @property
118 | def creation_dt(self):
119 | return self._creation_dt
120 |
121 | @property
122 | def version(self):
123 | return self._version
124 |
125 | @property
126 | def is_new(self):
127 | return self._dbc.is_new
128 |
129 | @property
130 | def in_memory(self):
131 | return self._dbc.in_memory
132 |
133 | @property
134 | def is_closed(self):
135 | return self._dbc.is_closed
136 |
137 | @property
138 | def is_destroyed(self):
139 | return self._dbc.is_destroyed
140 |
141 | def scan(self):
142 | """
143 | Scan the Jinbase database
144 |
145 | [returns]
146 | A dictionary object whose keys are jinbase.Model namedtuples
147 | and values are tuples of the total record count and total byte count.
148 | """
149 | model2store = {Model.DEPOT: self._depot,
150 | Model.KV: self._kv,
151 | Model.QUEUE: self._queue,
152 | Model.STACK: self._stack}
153 | return {model: (store.count_records(), store.count_bytes())
154 | for model, store in model2store.items()}
155 |
156 | @staticmethod
157 | def now():
158 | """
159 | Get the current utc datetime.
160 |
161 | [returns]
162 | A utc instance of `datetime.datetime`
163 | """
164 | return misc.now()
165 |
166 | @staticmethod
167 | def now_dt():
168 | """
169 | Get the current utc datetime.
170 |
171 | [returns]
172 | A utc string
173 | """
174 | return misc.now_dt()
175 |
176 | def latest(self):
177 | """
178 | Get the utc datetime of the latest operation.
179 |
180 | [returns]
181 | A utc instance of `datetime.datetime`
182 | """
183 | with self._dbc.cursor() as cur:
184 | timestamps = list()
185 | for model_name in [model.name.lower() for model in Model]:
186 | sql = queries.LATEST_WRITE.format(model=model_name)
187 | cur.execute(sql) # read
188 | r = cur.fetchone()
189 | if r is None:
190 | continue
191 | db_timestamp = r[0]
192 | timestamps.append(db_timestamp)
193 | db_timestamp = -1
194 | for t in timestamps:
195 | if t > db_timestamp:
196 | db_timestamp = t
197 | if db_timestamp == -1:
198 | return
199 | db_epoch = self._created_at
200 | return misc.get_datetime_str(db_epoch, db_timestamp,
201 | self._timestamp_precision)
202 |
203 | def count_records(self):
204 | with self._dbc.transaction() as cursor:
205 | n1 = self._kv.count_records()
206 | n2 = self._depot.count_records()
207 | n3 = self._queue.count_records()
208 | n4 = self._stack.count_records()
209 | return n1 + n2 + n3 + n4
210 |
211 | def count_bytes(self):
212 | with self._dbc.transaction() as cursor:
213 | n1 = self._kv.count_bytes()
214 | n2 = self._depot.count_bytes()
215 | n3 = self._queue.count_bytes()
216 | n4 = self._stack.count_bytes()
217 | return n1 + n2 + n3 + n4
218 |
219 | def count_chunks(self):
220 | with self._dbc.transaction() as cursor:
221 | n1 = self._kv.count_chunks()
222 | n2 = self._depot.count_chunks()
223 | n3 = self._queue.count_chunks()
224 | n4 = self._stack.count_chunks()
225 | return n1 + n2 + n3 + n4
226 |
227 | def transaction(self, transaction_mode=TransactionMode.DEFERRED):
228 | return self._dbc.transaction(transaction_mode=transaction_mode)
229 |
230 | def read_transaction(self):
231 | return self._dbc.transaction(transaction_mode=TransactionMode.DEFERRED)
232 |
233 | def write_transaction(self):
234 | return self._dbc.transaction(transaction_mode=TransactionMode.IMMEDIATE)
235 |
236 | def vacuum(self):
237 | """Vacuum the database"""
238 | self._dbc.vacuum()
239 |
240 | def vacuum_into(self, dst):
241 | """Vacuum into a file whose name is provided via `dst`."""
242 | self._dbc.vacuum_into(dst)
243 |
244 | def set_locking_mode(self, locking_mode):
245 | return self._dbc.set_locking_mode(locking_mode)
246 |
247 | def get_locking_mode(self):
248 | return self._dbc.get_locking_mode()
249 |
250 | def set_sync_mode(self, sync_mode):
251 | return self._dbc.set_sync_mode(sync_mode)
252 |
253 | def get_sync_mode(self):
254 | return self._dbc.get_sync_mode()
255 |
256 | def set_journal_mode(self, journal_mode):
257 | return self._dbc.set_journal_mode(journal_mode)
258 |
259 | def get_journal_mode(self):
260 | return self._dbc.get_journal_mode()
261 |
262 | def set_progress_handler(self, callback, n):
263 | return self._dbc.set_progress_handler(callback, n)
264 |
265 | def set_trace_callback(self, callback):
266 | return self._dbc.set_trace_callback(callback)
267 |
268 | def interrupt(self):
269 | return self._dbc.interrupt()
270 |
271 | def backup(self, dst, *, pages=-1,
272 | progress=None, sleep=0.250):
273 | self._dbc.backup(dst, pages=pages, progress=progress,
274 | sleep=sleep)
275 |
276 | def iterdump(self):
277 | """Returns an iterator to the dump of the database
278 | in an SQL text format"""
279 | return self._dbc.iterdump()
280 |
281 | def copy(self):
282 | """Create a new Jinbase instance that
283 | points to the same database file"""
284 | return self.__copy__()
285 |
286 | def close(self):
287 | """Close the connection"""
288 | return self._dbc.close()
289 |
290 | def destroy(self):
291 | """Destroy the database file"""
292 | return self._dbc.destroy()
293 |
294 | def __enter__(self):
295 | return self
296 |
297 | def __exit__(self, exc_type, exc_val, exc_tb):
298 | self.close()
299 |
300 | def __copy__(self):
301 | return Jinbase(self._filename, auto_create=self._auto_create,
302 | is_readonly=self._is_readonly, timeout=self._timeout,
303 | type_ref=self._type_ref, chunk_size=self._chunk_size)
304 |
305 |
306 | def create_dbc(filename, auto_create, is_readonly, timeout):
307 | def on_create_conn(dbc):
308 | with dbc.cursor() as cur:
309 | cur.executescript(queries.CONNECTION_DIRECTIVES,
310 | transaction_mode=None)
311 | dbc = LiteDBC(filename, auto_create=auto_create,
312 | is_readonly=is_readonly, timeout=timeout,
313 | on_create_conn=on_create_conn)
314 | return dbc
315 |
316 |
317 | def ensure_jinbase(dbc, chunk_size, timestamp_precision):
318 | sql = queries.GET_JINBASE_INFO
319 | if dbc.is_readonly:
320 | with dbc.cursor() as cur:
321 | cur.execute(sql)
322 | r = cur.fetchone()
323 | if r is None:
324 | msg = "Not a Jinbase file."
325 | raise Exception(msg)
326 | else:
327 | version, created_at, chunk_size, timestamp_precision = r
328 | return version, created_at, chunk_size, TimestampPrecision(timestamp_precision)
329 | else:
330 | with dbc.immediate_transaction() as cursor:
331 | sql = queries.GET_JINBASE_INFO
332 | cursor.execute(sql)
333 | r = cursor.fetchone()
334 | if r is None:
335 | sql = queries.SET_JINBASE_INFO
336 | version = const.JINBASE_VERSION
337 | created_at = misc.now()
338 | cursor.execute(sql, (version, created_at, chunk_size,
339 | timestamp_precision.value))
340 | else:
341 | version, created_at, chunk_size, timestamp_precision = r
342 | return version, created_at, chunk_size, TimestampPrecision(timestamp_precision)
343 |
--------------------------------------------------------------------------------
/src/jinbase/__main__.py:
--------------------------------------------------------------------------------
1 |
2 | __all__ = []
3 |
4 |
5 | def main():
6 | print("github.com/pyrustic/jinbase")
7 |
8 |
9 | if __name__ == "__main__":
10 | main()
11 |
--------------------------------------------------------------------------------
/src/jinbase/blob/__init__.py:
--------------------------------------------------------------------------------
1 | """The Blob class is defined here."""
2 | import os
3 | from jinbase import queries
4 |
5 |
6 | __all__ = ["Blob"]
7 |
8 |
9 | class Blob:
10 | """The Blob class allows a Read access to the blobs of Jinbase records.
11 | This class isn't intended to be directly instantiated by the user."""
12 | def __init__(self, store, record_id, n_bytes,
13 | n_chunks):
14 | """
15 | Initialization.
16 |
17 | [params]
18 | - store: Store instance.
19 | - record_id: The record's uid.
20 | - n_bytes: The size of the blob in bytes.
21 | - n_chunks: The number of chunks.
22 | """
23 | self._store = store
24 | self._record_id = record_id
25 | self._n_bytes = n_bytes
26 | self._n_chunks = n_chunks
27 | self._dbc = store.dbc
28 | self._model_name = store.model.name.lower()
29 | self._chunk_size = store.chunk_size
30 | self._position = 0
31 | self._slice_obj = slice(0, 0, 1)
32 | self._blob_io_files = dict()
33 |
34 | def read(self, length=-1, /):
35 | """
36 | Read the blob.
37 |
38 | [params]
39 | - length: The number of bytes to read.
40 | Defaults to -1 to mean the entire blob.
41 | Note that the cursor moves as reads are done.
42 |
43 | [return]
44 | Returns bytes or an empty byte.
45 | """
46 | data = self._read(self._position, length)
47 | self._position = update_position(self._position, len(data),
48 | os.SEEK_CUR, self._n_bytes)
49 | return data
50 |
51 | def write(self, data, /):
52 | """Jinbase doesn't allow Writes on blobs"""
53 | raise NotImplementedError # deliberately !
54 |
55 | def tell(self):
56 | """Returns the current position of the cursor"""
57 | return self._position
58 |
59 | def seek(self, offset, origin=os.SEEK_SET, /):
60 | """
61 | Move the cursor to another position
62 |
63 | [params]
64 | - offset: Offset value
65 | - origin: os.SEEK_SET, os.SEEK_CUR, or os.SEEK_END.
66 | Note that os.SEEK_END referes to position beyond the last
67 | character of the file, not the last character itself.
68 | """
69 | self._position = update_position(self._position,
70 | offset, origin,
71 | self._n_bytes)
72 |
73 | def close(self):
74 | """Close this Blob instance. Note that this method
75 | is automatically called by the Store's open_blob method.
76 | """
77 | for blob_io_file in self._blob_io_files.values():
78 | try:
79 | blob_io_file.close()
80 | except Exception as e:
81 | pass
82 |
83 | def _read(self, position, length):
84 | if length == 0 or position == self._n_chunks:
85 | return b''
86 | elif length < -1:
87 | msg = "Invalid length."
88 | raise ValueError(msg)
89 | start = position
90 | stop = self._n_bytes - 1 if length == -1 else start + length - 1
91 | stop = self._n_bytes -1 if stop >= self._n_bytes else stop
92 | blob_slices = get_blob_slices(start, stop, self._chunk_size)
93 | blob_slices = [blob_slice for blob_slice in blob_slices if blob_slice[0] <= self._n_chunks]
94 | if len(blob_slices) == 1:
95 | blob_slice = blob_slices[0]
96 | data = self._get_chunk(blob_slice)
97 | else:
98 | buffer = bytearray()
99 | for blob_slice in blob_slices:
100 | chunk = self._get_chunk(blob_slice)
101 | buffer.extend(chunk)
102 | data = bytes(buffer)
103 | return data
104 |
105 | def _get_blob_io_file(self, chunk_index):
106 | try:
107 | blob_io_file = self._blob_io_files[chunk_index]
108 | except KeyError as e:
109 | with self._dbc.cursor() as cur:
110 | sql = queries.GET_CHUNK_ID.format(model=self._model_name,
111 | offset=chunk_index)
112 | cur.execute(sql, (self._record_id,))
113 | r = cur.fetchone()
114 | if r is None:
115 | msg = "Failed to get 'chunk_id' for record {}".format(self._record_id)
116 | raise Exception(msg)
117 | chunk_id = r[0]
118 | table_name = "jinbase_{}_data".format(self._model_name)
119 | blob_io_file = self._dbc.blobopen(table_name, "chunk", chunk_id)
120 | self._blob_io_files[chunk_index] = blob_io_file
121 | return blob_io_file
122 |
123 | def _get_chunk(self, blob_slice):
124 | chunk_index, slice_obj = blob_slice
125 | if chunk_index == self._n_chunks:
126 | return b''
127 | elif chunk_index > self._n_chunks:
128 | msg = "BLOB index out of range for record {} (UID).".format(self._record_id)
129 | raise IndexError(msg)
130 | blob_io_file = self._get_blob_io_file(chunk_index)
131 | chunk = blob_io_file[slice_obj]
132 | return chunk
133 |
134 | def __getitem__(self, index):
135 | if isinstance(index, slice):
136 | slice_obj = index
137 | else:
138 | index = self._n_bytes + index if index < 0 else index
139 | slice_obj = slice(index, index + 1)
140 | slice_start, slice_stop, slice_step = slice_obj.indices(self._n_bytes)
141 | if slice_step != 1:
142 | msg = "The slice object should have 1 as step value."
143 | raise ValueError(msg)
144 | return self._read(slice_start, slice_stop-slice_start)
145 |
146 | def __setitem__(self, index, value):
147 | raise NotImplementedError # deliberately !
148 |
149 | def __delitem__(self, index):
150 | raise NotImplementedError # deliberately !
151 |
152 |
153 | def get_blob_slices(start_index, stop_index, chunk_size):
154 | blob_slices = list()
155 | chunk_index_1, sub_index_1 = divmod(start_index, chunk_size)
156 | chunk_index_2, sub_index_2 = divmod(stop_index, chunk_size)
157 | if start_index == stop_index:
158 | return ((chunk_index_1, slice(sub_index_2, sub_index_2 + 1)), )
159 | if chunk_index_1 == chunk_index_2:
160 | return ((chunk_index_1, slice(start_index, stop_index+1)), )
161 | blob_slices.append((chunk_index_1, slice(sub_index_1, chunk_size)))
162 | chunk_index = chunk_index_1
163 | for i in range(chunk_index_2-chunk_index_1-1):
164 | chunk_index += 1
165 | blob_slices.append((chunk_index, slice(0, chunk_size)))
166 | blob_slices.append((chunk_index+1, slice(0, sub_index_2+1)))
167 | return tuple(blob_slices)
168 |
169 |
170 | def update_position(cur_position, offset, origin, n_bytes):
171 | if origin == os.SEEK_SET:
172 | if offset < 0:
173 | msg = "Only positive offset is allowed with os.SEEK_SET."
174 | raise ValueError(msg)
175 | new_position = offset
176 | elif origin == os.SEEK_CUR:
177 | new_position = cur_position + offset
178 | elif origin == os.SEEK_END:
179 | if offset > 0:
180 | msg = "Only negative offset values are allowed with os.SEEK_END."
181 | raise ValueError(msg)
182 | new_position = n_bytes + offset
183 | else:
184 | msg = "Unsupported origin value."
185 | raise ValueError(msg)
186 | if new_position > n_bytes or new_position < 0:
187 | msg = "Offset out of range."
188 | raise ValueError(msg)
189 | return new_position
190 |
--------------------------------------------------------------------------------
/src/jinbase/const/__init__.py:
--------------------------------------------------------------------------------
1 | """Project-wide constants are defined in this module."""
2 | import os.path
3 | from enum import Enum, unique
4 |
5 | __all__ = ["Model", "TimestampPrecision",
6 | "TimeUnit", "StorageUnit", "CHUNK_SIZE", "JINBASE_HOME",
7 | "JINBASE_VERSION", "USER_HOME", "DATETIME_FORMAT",
8 | "TIMESTAMP_PRECISION", "TIMEOUT"]
9 |
10 |
11 | # models (key-value, depot, queue, and stack)
12 | @unique
13 | class Model(Enum):
14 | KV = 1
15 | DEPOT = 2
16 | QUEUE = 3
17 | STACK = 4
18 |
19 |
20 | @unique
21 | class TimestampPrecision(Enum):
22 | SECONDS = 0
23 | MILLISECONDS = 3
24 | MICROSECONDS = 6
25 | NANOSECONDS = 9
26 |
27 |
28 | @unique
29 | class StorageUnit(Enum):
30 | BYTE = "B"
31 | KIBIBYTE = "KiB"
32 | MEBIBYTE = "MiB"
33 | GIBIBYTE = "GiB"
34 | TEBIBYTE = "TiB"
35 |
36 |
37 | @unique
38 | class TimeUnit(Enum):
39 | SECOND = "sec"
40 | MINUTE = "min"
41 | HOUR = "hour"
42 | DAY = "day"
43 | WEEK = "week"
44 |
45 |
46 | # Default timestamp precision
47 | TIMESTAMP_PRECISION = TimestampPrecision.MILLISECONDS
48 |
49 |
50 | # directories
51 | USER_HOME = os.path.expanduser("~")
52 | JINBASE_HOME = os.path.join(USER_HOME, "JinbaseHome")
53 |
54 | # chunk size
55 | CHUNK_SIZE = 2**20 # 1 MiB
56 |
57 | # timeout
58 | TIMEOUT = 5.0
59 |
60 | # version
61 | JINBASE_VERSION = 1
62 |
63 | # datetime string
64 | DATETIME_FORMAT = "%Y-%m-%d %H:%M:%S.%fZ"
65 |
--------------------------------------------------------------------------------
/src/jinbase/errors/__init__.py:
--------------------------------------------------------------------------------
1 | """Exception classes are defined in this meodule."""
--------------------------------------------------------------------------------
/src/jinbase/misc/__init__.py:
--------------------------------------------------------------------------------
1 | """Misc functions"""
2 | import os
3 | import os.path
4 | import math
5 | from datetime import datetime, timezone
6 | from jinbase import const
7 |
8 |
9 | __all__ = []
10 |
11 |
12 | def now():
13 | return datetime.now(timezone.utc).strftime(const.DATETIME_FORMAT)
14 |
15 |
16 | def now_dt():
17 | return datetime.now(timezone.utc)
18 |
19 |
20 | def get_timestamp(epoch_dt, dt, timestamp_precision):
21 | """returns milliseconds"""
22 | timestamp_precision = const.TimestampPrecision(timestamp_precision)
23 | if isinstance(dt, str):
24 | dt = datetime.fromisoformat(dt)
25 | target_dt = dt.astimezone(tz=timezone.utc)
26 | epoch_dt = ensure_datetime(epoch_dt)
27 | t = target_dt.timestamp() - epoch_dt.timestamp()
28 | t = 0 if t < 0 else t
29 | return int(t * (10**timestamp_precision.value))
30 |
31 |
32 | def get_datetime(epoch_dt, timestamp, timestamp_precision):
33 | epoch_dt = ensure_datetime(epoch_dt)
34 | ts = epoch_dt.timestamp() + (timestamp / (10**timestamp_precision.value))
35 | return datetime.fromtimestamp(ts, tz=timezone.utc)
36 |
37 |
38 | def get_datetime_str(epoch_dt, timestamp, timestamp_precision):
39 | epoch_dt = ensure_datetime(epoch_dt)
40 | ts = epoch_dt.timestamp() + (timestamp / (10**timestamp_precision.value))
41 | return datetime.fromtimestamp(ts, tz=timezone.utc).strftime(const.DATETIME_FORMAT)
42 |
43 |
44 | def ensure_datatype(value, type_ref):
45 | value = type_ref.adapt(value)
46 | if value is None:
47 | return
48 | datatype = type_ref.check(type(value))
49 | if datatype is None:
50 | raise TypeError
51 | return datatype
52 |
53 |
54 | def ensure_datetime(dt):
55 | if isinstance(dt, str):
56 | # datetime.fromisoformat(dt_str) is faster than datetime.strptime(dt_str, format)
57 | # https://ehmatthes.com/blog/faster_than_strptime/
58 | # https://stackoverflow.com/questions/13468126/a-faster-strptime
59 | dt = datetime.fromisoformat(dt)
60 | return dt.astimezone(tz=timezone.utc)
61 |
62 |
63 | def split_bin(data, chunk_size):
64 | if chunk_size:
65 | for i in range(0, len(data), chunk_size):
66 | yield data[i:i+chunk_size]
67 | else:
68 | yield data
69 |
70 |
71 | def time_range_to_timestamps(epoch_dt, time_range, timestamp_precision):
72 | begin, end = time_range
73 | begin = epoch_dt if begin is None else begin
74 | end = now_dt() if end is None else end
75 | timestamp_begin = get_timestamp(epoch_dt, begin, timestamp_precision)
76 | timestamp_end = get_timestamp(epoch_dt, end, timestamp_precision)
77 | if timestamp_begin > timestamp_end:
78 | x = timestamp_begin
79 | timestamp_begin = timestamp_end
80 | timestamp_end = x
81 | return timestamp_begin, timestamp_end
82 |
83 |
84 | def get_limit_spec(limit):
85 | if limit is None:
86 | return ""
87 | return "LIMIT {}".format(int(limit))
88 |
89 |
90 | def create_backup_filename(db_filename):
91 | current_datetime = datetime.now()
92 | dt = current_datetime.strftime("%Y-%m-%dT%H:%M:%S")
93 | basename, ext = os.path.splitext(os.path.basename(db_filename))
94 | return "{dt}_{basename}_backup{ext}".format(dt=dt,
95 | basename=basename,
96 | ext=ext)
97 |
98 |
99 | def convert_size(size):
100 | """ Size should be in bytes.
101 | Return a tuple (float_or_int_val, StorageUnit instance) """
102 | if size == 0:
103 | return 0, const.StorageUnit.BYTE
104 | kib = 1024
105 | units = list(const.StorageUnit)
106 | i = int(math.floor(math.log(size, kib)))
107 | p = math.pow(kib, i)
108 | result = round(size/p, 2)
109 | if result.is_integer():
110 | result = int(result)
111 | return result, units[i]
112 |
113 |
114 | def calc_duration(dt1, dt2=None):
115 | dt1 = ensure_datetime(dt1)
116 | dt2 = now_dt() if dt2 is None else ensure_datetime(dt2)
117 | time_diff = abs(dt1 - dt2)
118 | total_seconds = time_diff.total_seconds()
119 | total_minutes = total_seconds / 60
120 | total_hours = total_minutes / 60
121 | total_days = total_hours / 24
122 | total_weeks = total_days / 7
123 | if total_weeks >= 1:
124 | result, unit = round(total_weeks, 2), const.TimeUnit.WEEK
125 | elif total_days >= 1:
126 | result, unit = round(total_days, 2), const.TimeUnit.DAY
127 | elif total_hours >= 1:
128 | result, unit = round(total_hours, 2), const.TimeUnit.HOUR
129 | elif total_minutes >= 1:
130 | result, unit = round(total_minutes, 2), const.TimeUnit.MINUTE
131 | else:
132 | result, unit = round(total_seconds, 2), const.TimeUnit.SECOND
133 | if result.is_integer():
134 | result = int(result)
135 | return result, unit
136 |
--------------------------------------------------------------------------------
/src/jinbase/queries/__init__.py:
--------------------------------------------------------------------------------
1 | """All SQL queries are defined in this module."""
2 |
3 |
4 | __all__ = []
5 |
6 |
7 | # Init script
8 | INIT_SCRIPT = """
9 |
10 | -- Create the JINBASE_INFO table
11 | CREATE TABLE IF NOT EXISTS jinbase_info (
12 | id INTEGER NOT NULL UNIQUE DEFAULT 0,
13 | version INTEGER NOT NULL,
14 | created_at TEXT NOT NULL,
15 | chunk_size INTEGER NOT NULL,
16 | timestamp_precision INTEGER NOT NULL,
17 | CONSTRAINT chk_id
18 | CHECK (id == 0));
19 |
20 |
21 | -- Create the JINBASE_KV_RECORD table
22 | CREATE TABLE IF NOT EXISTS jinbase_kv_record (
23 | id INTEGER PRIMARY KEY AUTOINCREMENT,
24 | datatype INTEGER NOT NULL,
25 | timestamp INTEGER NOT NULL,
26 | int_key INTEGER UNIQUE,
27 | str_key TEXT UNIQUE,
28 | CONSTRAINT chk_key
29 | CHECK ((int_key IS NULL AND str_key IS NOT NULL)
30 | OR
31 | (int_key IS NOT NULL AND str_key IS NULL)));
32 |
33 | -- Create index for JINBASE_KV_RECORD's timestamp
34 | CREATE INDEX IF NOT EXISTS idx_jinbase_kv_record_timestamp
35 | ON jinbase_kv_record (timestamp);
36 |
37 | -- Create the JINBASE_KV_DATA table
38 | CREATE TABLE IF NOT EXISTS jinbase_kv_data (
39 | id INTEGER PRIMARY KEY AUTOINCREMENT,
40 | record_id INTEGER NOT NULL,
41 | chunk BLOB NOT NULL,
42 | CONSTRAINT fk_jinbase_kv_data_record_id
43 | FOREIGN KEY (record_id)
44 | REFERENCES jinbase_kv_record(id)
45 | ON DELETE CASCADE);
46 |
47 | -- Create index for JINBASE_KV_DATA's record_id
48 | CREATE INDEX IF NOT EXISTS idx_jinbase_kv_data_record_id
49 | ON jinbase_kv_data (record_id);
50 |
51 | -- Create the JINBASE_KV_POINTER table
52 | CREATE TABLE IF NOT EXISTS jinbase_kv_pointer (
53 | field TEXT NOT NULL,
54 | record_id INTEGER NOT NULL,
55 | slice_start INTEGER NOT NULL,
56 | slice_stop INTEGER NOT NULL,
57 | PRIMARY KEY (field, record_id),
58 | CONSTRAINT fk_jinbase_kv_pointer_record_id
59 | FOREIGN KEY (record_id)
60 | REFERENCES jinbase_kv_record(id)
61 | ON DELETE CASCADE);
62 |
63 | -- Create index for JINBASE_KV_POINTER's record_id
64 | CREATE INDEX IF NOT EXISTS idx_jinbase_kv_pointer_record_id
65 | ON jinbase_kv_pointer (record_id);
66 |
67 |
68 | -- Create the JINBASE_DEPOT_RECORD table
69 | CREATE TABLE IF NOT EXISTS jinbase_depot_record (
70 | id INTEGER PRIMARY KEY AUTOINCREMENT,
71 | datatype INTEGER NOT NULL,
72 | timestamp INTEGER NOT NULL);
73 |
74 | -- Create index for JINBASE_DEPOT_RECORD's timestamp
75 | CREATE INDEX IF NOT EXISTS idx_jinbase_depot_record_timestamp
76 | ON jinbase_depot_record (timestamp);
77 |
78 | -- Create the JINBASE_DEPOT_DATA table
79 | CREATE TABLE IF NOT EXISTS jinbase_depot_data (
80 | id INTEGER PRIMARY KEY AUTOINCREMENT,
81 | record_id INTEGER NOT NULL,
82 | chunk BLOB NOT NULL,
83 | CONSTRAINT fk_jinbase_depot_data_record_id
84 | FOREIGN KEY (record_id)
85 | REFERENCES jinbase_depot_record(id)
86 | ON DELETE CASCADE);
87 |
88 | -- Create index for JINBASE_DEPOT_DATA's record_id
89 | CREATE INDEX IF NOT EXISTS idx_jinbase_depot_data_record_id
90 | ON jinbase_depot_data (record_id);
91 |
92 | -- Create the JINBASE_DEPOT_POINTER table
93 | CREATE TABLE IF NOT EXISTS jinbase_depot_pointer (
94 | field TEXT NOT NULL,
95 | record_id INTEGER NOT NULL,
96 | slice_start INTEGER NOT NULL,
97 | slice_stop INTEGER NOT NULL,
98 | PRIMARY KEY (field, record_id),
99 | CONSTRAINT fk_jinbase_depot_pointer_record_id
100 | FOREIGN KEY (record_id)
101 | REFERENCES jinbase_depot_record(id)
102 | ON DELETE CASCADE);
103 |
104 | -- Create index for JINBASE_DEPOT_POINTER's record_id
105 | CREATE INDEX IF NOT EXISTS idx_jinbase_depot_pointer_record_id
106 | ON jinbase_depot_pointer (record_id);
107 |
108 |
109 | -- Create the JINBASE_QUEUE_RECORD table
110 | CREATE TABLE IF NOT EXISTS jinbase_queue_record (
111 | id INTEGER PRIMARY KEY AUTOINCREMENT,
112 | datatype INTEGER NOT NULL,
113 | timestamp INTEGER NOT NULL);
114 |
115 | -- Create index for JINBASE_QUEUE_RECORD's timestamp
116 | CREATE INDEX IF NOT EXISTS idx_jinbase_queue_record_timestamp
117 | ON jinbase_queue_record (timestamp);
118 |
119 | -- Create the JINBASE_QUEUE_DATA table
120 | CREATE TABLE IF NOT EXISTS jinbase_queue_data (
121 | id INTEGER PRIMARY KEY AUTOINCREMENT,
122 | record_id INTEGER NOT NULL,
123 | chunk BLOB NOT NULL,
124 | CONSTRAINT fk_jinbase_queue_data_record_id
125 | FOREIGN KEY (record_id)
126 | REFERENCES jinbase_queue_record(id)
127 | ON DELETE CASCADE);
128 |
129 | -- Create index for JINBASE_QUEUE_DATA's record_id
130 | CREATE INDEX IF NOT EXISTS idx_jinbase_queue_data_record_id
131 | ON jinbase_queue_data (record_id);
132 |
133 |
134 | -- Create the JINBASE_STACK_RECORD table
135 | CREATE TABLE IF NOT EXISTS jinbase_stack_record (
136 | id INTEGER PRIMARY KEY AUTOINCREMENT,
137 | datatype INTEGER NOT NULL,
138 | timestamp INTEGER NOT NULL);
139 |
140 | -- Create index for JINBASE_STACK_RECORD's timestamp
141 | CREATE INDEX IF NOT EXISTS idx_jinbase_stack_record_timestamp
142 | ON jinbase_stack_record (timestamp);
143 |
144 | -- Create the JINBASE_STACK_DATA table
145 | CREATE TABLE IF NOT EXISTS jinbase_stack_data (
146 | id INTEGER PRIMARY KEY AUTOINCREMENT,
147 | record_id INTEGER NOT NULL,
148 | chunk BLOB NOT NULL,
149 | CONSTRAINT fk_jinbase_stack_data_record_id
150 | FOREIGN KEY (record_id)
151 | REFERENCES jinbase_stack_record(id)
152 | ON DELETE CASCADE);
153 |
154 | -- Create index for JINBASE_STACK_DATA's record_id
155 | CREATE INDEX IF NOT EXISTS idx_jinbase_stack_data_record_id
156 | ON jinbase_stack_data (record_id);
157 | """
158 |
159 |
160 | # PRAGMA to run at connection creation
161 | CONNECTION_DIRECTIVES = """
162 | PRAGMA foreign_keys=ON;
163 | PRAGMA synchronous=NORMAL;
164 | """
165 |
166 |
167 | # Jinbase info
168 | GET_JINBASE_INFO = """
169 | SELECT version, created_at, chunk_size, timestamp_precision FROM jinbase_info
170 | """
171 | SET_JINBASE_INFO = """
172 | INSERT INTO jinbase_info (version, created_at, chunk_size, timestamp_precision)
173 | VALUES (?, ?, ?, ?)
174 | """
175 |
176 |
177 | # Record management
178 | LATEST_WRITE = """
179 | SELECT timestamp FROM jinbase_{model}_record ORDER BY timestamp DESC LIMIT 1
180 | """
181 | COUNT_RECORDS = """
182 | SELECT COUNT(*) AS n FROM jinbase_{model}_record
183 | """
184 | RETRIEVE_RECORDS = """
185 | SELECT id FROM jinbase_{model}_record WHERE ORDER BY id
186 | """
187 | DELETE_RECORD = """
188 | DELETE FROM jinbase_{model}_record WHERE id=?
189 | """
190 | DELETE_RECORDS = """
191 | DELETE FROM jinbase_{model}_record
192 | """
193 |
194 |
195 | # Data management
196 | GET_CHUNK_ID = """
197 | SELECT id FROM jinbase_{model}_data WHERE record_id = ?
198 | ORDER BY id LIMIT 1 OFFSET {offset}
199 | """
200 | STORE_DATA = """
201 | INSERT INTO jinbase_{model}_data (record_id, chunk) VALUES (?, ?)
202 | """
203 | RETRIEVE_DATA = """
204 | SELECT chunk FROM jinbase_{model}_data WHERE record_id=? ORDER BY id
205 | """
206 | COUNT_STORE_CHUNKS = """SELECT COUNT(*) AS n FROM jinbase_{model}_data
207 | """
208 | COUNT_STORE_BYTES = """
209 | SELECT SUM(LENGTH(chunk)) AS n FROM jinbase_{model}_data
210 | """
211 | COUNT_RECORD_BYTES = """
212 | SELECT SUM(LENGTH(chunk)) AS n FROM jinbase_{model}_data WHERE record_id = ?
213 | """
214 | COUNT_RECORD_CHUNKS = """
215 | SELECT COUNT(*) AS n FROM jinbase_{model}_data WHERE record_id = ?
216 | """
217 |
218 | # Pointer management
219 | ADD_POINTER = """
220 | INSERT INTO jinbase_{model}_pointer (field, record_id, slice_start, slice_stop)
221 | VALUES (?, ?, ?, ?)
222 | """
223 | GET_POINTER = """
224 | SELECT slice_start, slice_stop FROM jinbase_{model}_pointer WHERE field = ? AND record_id = ?
225 | """
226 | GET_POINTED_FIELDS = """
227 | SELECT field FROM jinbase_{model}_pointer ORDER BY field
228 | """
229 |
230 |
231 | # Key-value store
232 | COUNT_KEY_OCCURRENCE = """
233 | SELECT COUNT(*) AS n FROM jinbase_kv_record WHERE {key_type}_key=?
234 | """
235 | SET_KV_RECORD = """
236 | INSERT INTO jinbase_kv_record (datatype, timestamp, {key_type}_key)
237 | VALUES (?, ?, ?)
238 | """
239 | GET_KV_RECORD_BY_KEY = """
240 | SELECT id, datatype, timestamp FROM jinbase_kv_record WHERE {key_type}_key=?
241 | """
242 | GET_KV_KEY_BY_UID = """
243 | SELECT
244 | CASE
245 | WHEN int_key IS NOT NULL THEN int_key
246 | ELSE str_key
247 | END AS key
248 | FROM jinbase_kv_record WHERE id=?
249 | """
250 | SELECT_KEYS = """
251 | SELECT
252 | CASE
253 | WHEN int_key IS NOT NULL THEN int_key
254 | ELSE str_key
255 | END AS key
256 | FROM jinbase_kv_record {criteria} ORDER BY key {sort_order} {limit}
257 | """
258 | SELECT_INT_KEYS = """
259 | SELECT int_key as key
260 | FROM jinbase_kv_record
261 | WHERE int_key IS NOT NULL {criteria}
262 | ORDER BY key {sort_order} {limit}
263 | """
264 | SELECT_STR_KEYS = """
265 | SELECT str_key as key
266 | FROM jinbase_kv_record
267 | WHERE str_key IS NOT NULL {criteria}
268 | ORDER BY key {sort_order} {limit}
269 | """
270 | SELECT_STR_KEYS_WITH_GLOB = """
271 | SELECT str_key as key
272 | FROM jinbase_kv_record
273 | WHERE str_key IS NOT NULL AND str_key GLOB ? {criteria}
274 | ORDER BY key {sort_order} {limit}
275 | """
276 | KV_CRITERIA_1 = "int_key >= {val}"
277 | KV_CRITERIA_2 = "int_key <= {val}"
278 | KV_CRITERIA_3 = "int_key BETWEEN {first} AND {last}"
279 | KV_CRITERIA_4 = "timestamp BETWEEN {start} AND {stop}"
280 |
281 |
282 | # Depot store
283 | GET_DEPOT_RECORD = """
284 | SELECT datatype, timestamp
285 | FROM jinbase_depot_record WHERE id = ?
286 | """
287 | GET_DEPOT_RECORD_BY_POSITION = """
288 | SELECT id, datatype, timestamp
289 | FROM jinbase_depot_record ORDER BY id LIMIT 1 OFFSET {offset}
290 | """
291 | APPEND_TO_DEPOT = """
292 | INSERT INTO jinbase_depot_record (datatype, timestamp) VALUES (?, ?)
293 | """
294 | GET_DEPOT_RECORDS_BETWEEN_TIMESTAMPS = """
295 | SELECT id FROM jinbase_depot_record WHERE timestamp BETWEEN ? AND ?
296 | ORDER BY id {sort_order} {limit}
297 | """
298 | COUNT_DEPOT_RECORD_OFFSET = """
299 | SELECT COUNT(*) AS n FROM jinbase_depot_record WHERE id <= ?
300 | ORDER BY id
301 | """
302 |
303 |
304 |
305 | # Queue store
306 | GET_QUEUE_FRONT = """
307 | SELECT id, datatype, timestamp
308 | FROM jinbase_queue_record ORDER BY id LIMIT 1
309 | """
310 | GET_QUEUE_FRONT_UID = """
311 | SELECT id FROM jinbase_queue_record ORDER BY id LIMIT 1
312 | """
313 | GET_QUEUE_BACK = """
314 | SELECT id, datatype, timestamp
315 | FROM jinbase_queue_record ORDER BY id DESC LIMIT 1
316 | """
317 | GET_QUEUE_BACK_UID = """
318 | SELECT id FROM jinbase_queue_record ORDER BY id DESC LIMIT 1
319 | """
320 | ENQUEUE = """
321 | INSERT INTO jinbase_queue_record (datatype, timestamp) VALUES (?, ?)
322 | """
323 |
324 |
325 | # Stack store
326 | STACK_PUSH = """
327 | INSERT INTO jinbase_stack_record (datatype, timestamp) VALUES (?, ?)
328 | """
329 | GET_STACK_TOP = """
330 | SELECT id, datatype, timestamp FROM jinbase_stack_record ORDER BY id DESC LIMIT 1
331 | """
332 | GET_STACK_TOP_UID = """
333 | SELECT id FROM jinbase_stack_record ORDER BY id DESC LIMIT 1
334 | """
335 |
--------------------------------------------------------------------------------
/src/jinbase/store/__init__.py:
--------------------------------------------------------------------------------
1 | """The abstract Store class is defined in this module."""
2 | from abc import ABC
3 | from collections import namedtuple
4 | from paradict import Unpacker, Packer, Datatype
5 | from litedbc import TransactionMode
6 | from jinbase import misc
7 | from jinbase import queries
8 | from jinbase.const import Model
9 |
10 |
11 | __all__ = ["Store", "RecordInfo"]
12 |
13 |
14 | RecordInfo = namedtuple("RecordInfo",
15 | ("uid", "datatype", "created_at"))
16 | RecordInfo.__doc__ = """\
17 | Named tuple returned by store.info()
18 |
19 | [params]
20 | uid: The record id
21 | datatype: An instance of `paradict.Datatype`
22 | created_at: Datetime string representing the creation datetime of the record
23 | """
24 |
25 |
26 | class Store(ABC):
27 | """Abstract Store class intended to be subclassed by the
28 | Kv, Depot, Queue, and Stack stores"""
29 | def __init__(self, model, jinbase):
30 | """Init.
31 |
32 | [params]
33 | - model: A Model namedtuple instance
34 | - jinbase: Jinbase instance
35 | """
36 | self._model = Model(model)
37 | self._model_name = self._model.name.lower()
38 | self._jinbase = jinbase
39 | self._db_epoch = jinbase.created_at
40 | self._timestamp_precision = jinbase.timestamp_precision
41 | self._dbc = jinbase.dbc
42 | self._type_ref = jinbase.type_ref
43 | self._chunk_size = jinbase.chunk_size
44 |
45 | @property
46 | def model(self):
47 | return self._model
48 |
49 | @property
50 | def jinbase(self):
51 | return self._jinbase
52 |
53 | @property
54 | def filename(self):
55 | return self._dbc.filename
56 |
57 | @property
58 | def is_readonly(self):
59 | return self._dbc.is_readonly
60 |
61 | @property
62 | def timeout(self):
63 | return self._dbc.timeout
64 |
65 | @property
66 | def type_ref(self):
67 | return self._jinbase.type_ref
68 |
69 | @property
70 | def chunk_size(self):
71 | return self._jinbase.chunk_size
72 |
73 | @property
74 | def dbc(self):
75 | return self._dbc
76 |
77 | @property
78 | def is_new(self):
79 | return self._dbc.is_new
80 |
81 | @property
82 | def in_memory(self):
83 | return self._dbc.in_memory
84 |
85 | @property
86 | def is_closed(self):
87 | return self._dbc.is_closed
88 |
89 | def transaction(self, transaction_mode=TransactionMode.DEFERRED):
90 | """
91 | Context manager for executing a transaction.
92 |
93 | [params]
94 | - transaction: Instance of `litedbc.TransactionMode`
95 | """
96 | return self._dbc.transaction(transaction_mode=transaction_mode)
97 |
98 | def read_transaction(self):
99 | """
100 | Context manager for executing a Read transaction.
101 |
102 | [yield]
103 | Yields a `litedbc.Cursor` object
104 | """
105 | return self._dbc.transaction(transaction_mode=TransactionMode.DEFERRED)
106 |
107 | def write_transaction(self):
108 | """
109 | Context manager for executing a Write transaction.
110 |
111 | [yield]
112 | Yields a `litedbc.Cursor` object
113 | """
114 | return self._dbc.transaction(transaction_mode=TransactionMode.IMMEDIATE)
115 |
116 | def count_records(self):
117 | """
118 | Count all records in the store.
119 |
120 | [return]
121 | Returns the number of records
122 | """
123 | with self._dbc.cursor() as cur:
124 | sql = queries.COUNT_RECORDS.format(model=self._model_name)
125 | cur.execute(sql) # read
126 | r = cur.fetchone()[0]
127 | return r if r else 0
128 |
129 | def count_bytes(self):
130 | """
131 | Count all data bytes in the store.
132 |
133 | [return]
134 | Returns the count of data bytes"""
135 | with self._dbc.cursor() as cur:
136 | sql = queries.COUNT_STORE_BYTES.format(model=self._model_name)
137 | cur.execute(sql) # read
138 | r = cur.fetchone()[0]
139 | return r if r else 0
140 |
141 | def count_chunks(self):
142 | """
143 | Count all data chunks in the store.
144 |
145 | [return]
146 | Returns the number of chunks"""
147 | with self._dbc.cursor() as cur:
148 | sql = queries.COUNT_STORE_CHUNKS.format(model=self._model_name)
149 | cur.execute(sql) # read
150 | r = cur.fetchone()[0]
151 | return r if r else 0
152 |
153 | def is_empty(self):
154 | """
155 | Tells whether the store is empty or not
156 |
157 | [return]
158 | Return a boolean.
159 | """
160 | return True if self.count_records() == 0 else False
161 |
162 | @staticmethod
163 | def now():
164 | """
165 | Get the current datetime.
166 |
167 | [return]
168 | Return a datetime string.
169 | """
170 | return misc.now()
171 |
172 | @staticmethod
173 | def now_dt():
174 | """
175 | Get the current datetime.
176 |
177 | [return]
178 | Return a datetime object.
179 | """
180 | return misc.now_dt()
181 |
182 | def latest(self):
183 | """
184 | Retrieve the datetime of the latest write operation.
185 |
186 | [return]
187 | Return a datetime string
188 | """
189 | with self._dbc.cursor() as cur:
190 | sql = queries.LATEST_WRITE.format(model=self._model_name)
191 | cur.execute(sql) # read
192 | r = cur.fetchone()
193 | if r is None:
194 | return
195 | db_timestamp = r[0]
196 | return misc.get_datetime_str(self._db_epoch, db_timestamp,
197 | self._timestamp_precision)
198 |
199 | def delete_all(self):
200 | """Delete all records in the store"""
201 | with self._dbc.cursor() as cur:
202 | sql = queries.DELETE_RECORDS.format(model=self._model_name)
203 | cur.execute(sql) # write
204 |
205 | def _store_data(self, record_id, datatype, value):
206 | with self._dbc.cursor() as cur:
207 | sql = queries.STORE_DATA.format(model=self._model_name)
208 | if datatype == Datatype.BIN:
209 | for chunk in misc.split_bin(value, chunk_size=self._chunk_size):
210 | cur.execute(sql, (record_id, chunk))
211 | else:
212 | buffer = bytearray()
213 | packer = Packer(type_ref=self._type_ref, auto_index=True)
214 | for x in packer.pack(value):
215 | buffer.extend(x)
216 | while len(buffer) >= self._chunk_size:
217 | chunk = buffer[:self._chunk_size]
218 | del buffer[:self._chunk_size]
219 | cur.execute(sql, (record_id, chunk))
220 | if buffer:
221 | cur.execute(sql, (record_id, buffer))
222 | # create pointers
223 | if datatype == Datatype.DICT and self._model in (Model.KV,
224 | Model.DEPOT):
225 | sql = queries.ADD_POINTER.format(model=self._model_name)
226 | for field, slice_obj in packer.index_dict.items():
227 | if isinstance(field, str):
228 | cur.execute(sql, (field,
229 | record_id,
230 | slice_obj.start,
231 | slice_obj.stop))
232 |
233 | def _retrieve_data(self, record_id, datatype):
234 | with self._dbc.cursor() as cur:
235 | is_serialized = False if datatype == Datatype.BIN else True
236 | sql = queries.RETRIEVE_DATA.format(model=self._model_name)
237 | chunks = bytearray()
238 | unpacker = Unpacker(type_ref=self._type_ref)
239 | cur.execute(sql, (record_id, ))
240 | for row in cur.fetch():
241 | chunk = row[0]
242 | if is_serialized:
243 | unpacker.feed(chunk)
244 | else:
245 | chunks.extend(chunk)
246 | if is_serialized:
247 | return unpacker.data
248 | else:
249 | return self._type_ref.bin_type(chunks)
250 |
251 | def _delete_record(self, record_id):
252 | with self._dbc.cursor() as cur:
253 | sql = queries.DELETE_RECORD.format(model=self._model_name)
254 | cur.execute(sql, (record_id, ))
255 | return cur.rowcount
256 |
--------------------------------------------------------------------------------
/src/jinbase/store/depot.py:
--------------------------------------------------------------------------------
1 | """The Depot store is defined in this module."""
2 | from contextlib import contextmanager
3 | from paradict import Datatype, unpack
4 | from jinbase import queries, misc
5 | from jinbase.const import Model
6 | from jinbase.store import Store, RecordInfo
7 | from jinbase.blob import Blob
8 |
9 |
10 | __all__ = ["Depot"]
11 |
12 |
13 | class Depot(Store):
14 | """
15 | This class represents the Depot store.
16 | Note that a Depot object isn't intended to be directly
17 | instantiated by the user.
18 | """
19 | def __init__(self, jinbase):
20 | """
21 | Init
22 |
23 | [params]
24 | - jinbase: Jinbase object
25 | """
26 | super().__init__(Model.DEPOT, jinbase)
27 |
28 | def exists(self, uid):
29 | r = self._get_record(uid)
30 | if r is None: # nonexistent
31 | return False
32 | return True
33 |
34 | def info(self, uid):
35 | # returns a paradict.Datatype instance + creation datetime
36 | r = self._get_record(uid)
37 | if r is None: # nonexistent
38 | return
39 | datatype, db_timestamp = r
40 | created_at = misc.get_datetime_str(self._db_epoch, db_timestamp,
41 | self._timestamp_precision)
42 | return RecordInfo(uid=uid, datatype=datatype, created_at=created_at)
43 |
44 | def get(self, uid, default=None):
45 | with self._dbc.transaction():
46 | r = self._get_record(uid) # read
47 | if r is None: # nonexistent
48 | return default
49 | datatype, _ = r
50 | return self._retrieve_data(uid, datatype) # read
51 |
52 | def get_first(self, default=None):
53 | with self._dbc.transaction() as cursor:
54 | uid = self.uid(0)
55 | if uid is None:
56 | return default
57 | return self.get(uid, default=default)
58 |
59 | def get_last(self, default=None):
60 | with self._dbc.transaction() as cursor:
61 | uid = self.uid(-1)
62 | if uid is None:
63 | return default
64 | return self.get(uid, default=default)
65 |
66 | def append(self, value):
67 | if value is None:
68 | return
69 | with self._dbc.immediate_transaction() as cursor:
70 | value = self._type_ref.adapt(value)
71 | datatype = misc.ensure_datatype(value, self._type_ref)
72 | if datatype is None:
73 | raise TypeError
74 | sql = queries.APPEND_TO_DEPOT
75 | db_timestamp = misc.get_timestamp(self._db_epoch, misc.now_dt(),
76 | self._timestamp_precision)
77 | cursor.execute(sql, (datatype.value, db_timestamp)) # write
78 | record_id = cursor.lastrowid
79 | self._store_data(record_id, datatype, value) # write
80 | return record_id
81 |
82 | def extend(self, values):
83 | with self._dbc.immediate_transaction() as cursor:
84 | uids = list()
85 | for value in values:
86 | uid = self.append(value) #writeS
87 | uids.append(uid)
88 | return tuple(uids)
89 |
90 | def uid(self, position):
91 | with self._dbc.transaction() as cursor:
92 | try:
93 | position = _ensure_position(self, position) # possible read
94 | except IndexError as e:
95 | return
96 | r = self._get_record_by_position(position) # read
97 | if r is None:
98 | return
99 | record_id, _, _ = r
100 | return record_id
101 |
102 | def position(self, uid):
103 | with self._dbc.transaction() as cursor:
104 | if not self.exists(uid):
105 | return
106 | sql = queries.COUNT_DEPOT_RECORD_OFFSET
107 | cursor.execute(sql, (uid,))
108 | r = cursor.fetchone()[0]
109 | return r - 1
110 |
111 | def uids(self, *, time_range=None, limit=None, asc=True):
112 | with self._dbc.cursor() as cur:
113 | if time_range is None:
114 | start, stop = 0, misc.get_timestamp(self._db_epoch, misc.now_dt(),
115 | self._timestamp_precision)
116 | else:
117 | timestamps = misc.time_range_to_timestamps(self._db_epoch, time_range,
118 | self._timestamp_precision)
119 | start, stop = timestamps
120 | # retrieve uids
121 | sort_order = "ASC" if asc else "DESC"
122 | limit = misc.get_limit_spec(limit)
123 | sql = queries.GET_DEPOT_RECORDS_BETWEEN_TIMESTAMPS.format(sort_order=sort_order,
124 | limit=limit)
125 | cur.execute(sql, (start, stop))
126 | for row in cur.fetch():
127 | uid = row[0]
128 | yield uid
129 |
130 | def iterate(self, *, time_range=None, limit=None, asc=True):
131 | for uid in self.uids(time_range=time_range, limit=limit, asc=asc):
132 | yield uid, self.get(uid)
133 |
134 | def count_bytes(self, uid=None):
135 | if uid is None:
136 | return super().count_bytes()
137 | with self._dbc.transaction() as cur:
138 | r = self._get_record(uid) # read
139 | if r is None:
140 | return 0
141 | sql = queries.COUNT_RECORD_BYTES.format(model=self._model_name)
142 | cur.execute(sql, (uid,)) # read
143 | r = cur.fetchone()[0]
144 | return r if r else 0
145 |
146 | def count_chunks(self, uid=None):
147 | if uid is None:
148 | return super().count_chunks()
149 | with self._dbc.transaction() as cur:
150 | r = self._get_record(uid) # read
151 | if r is None:
152 | return 0
153 | sql = queries.COUNT_RECORD_CHUNKS.format(model=self._model_name)
154 | cur.execute(sql, (uid,)) # read
155 | r = cur.fetchone()[0]
156 | return r if r else 0
157 |
158 | @contextmanager
159 | def open_blob(self, uid):
160 | with self._dbc.transaction() as cursor:
161 | n_chunks = self.count_chunks(uid)
162 | n_bytes = self.count_bytes(uid)
163 | blob = Blob(self, uid, n_bytes, n_chunks)
164 | try:
165 | yield blob
166 | finally:
167 | blob.close()
168 |
169 | def load_field(self, uid, field, default=None):
170 | with self._dbc.transaction() as cur:
171 | sql = queries.GET_POINTER.format(model=self._model_name)
172 | cur.execute(sql, (field, uid)) # read
173 | r = cur.fetchone()
174 | if r is None:
175 | return default
176 | slice_obj = slice(*r)
177 | with self.open_blob(uid) as blob:
178 | data = blob[slice_obj]
179 | return unpack(data)
180 |
181 | def fields(self):
182 | with self._dbc.transaction() as cur:
183 | sql = queries.GET_POINTED_FIELDS.format(model=self._model_name)
184 | cur.execute(sql) # read
185 | for r in cur.fetch():
186 | yield r[0]
187 |
188 | def delete(self, uid):
189 | with self._dbc.immediate_transaction() as cursor:
190 | n = self._delete_record(uid) # write
191 | return True if n > 0 else False
192 |
193 | def delete_many(self, uids):
194 | with self._dbc.immediate_transaction() as cursor:
195 | deleted_uids = list()
196 | for uid in uids:
197 | if self.delete(uid):
198 | deleted_uids.append(uid)
199 | return tuple(deleted_uids)
200 |
201 | def _get_record(self, uid):
202 | with self._dbc.cursor() as cur:
203 | sql = queries.GET_DEPOT_RECORD
204 | cur.execute(sql, (uid,))
205 | r = cur.fetchone()
206 | if r is None: # nonexistent
207 | return
208 | dtype, db_timestamp = r
209 | return Datatype(dtype), db_timestamp
210 |
211 | def _get_record_by_position(self, position):
212 | with self._dbc.cursor() as cur:
213 | sql = queries.GET_DEPOT_RECORD_BY_POSITION.format(offset=position)
214 | cur.execute(sql)
215 | r = cur.fetchone()
216 | if r is None: # nonexistent
217 | return
218 | record_id, dtype, db_timestamp = r
219 | return record_id, Datatype(dtype), db_timestamp
220 |
221 |
222 | def _ensure_position(store, position):
223 | position = int(position)
224 | if position >= 0:
225 | return position
226 | n = store.count_records()
227 | abs_position = abs(position)
228 | if abs_position > n:
229 | raise IndexError
230 | return n - abs_position
231 |
--------------------------------------------------------------------------------
/src/jinbase/store/queue.py:
--------------------------------------------------------------------------------
1 | """The Queue store is defined in this module."""
2 | from paradict import Datatype
3 | from jinbase import queries, misc
4 | from jinbase.const import Model
5 | from jinbase.store import Store, RecordInfo
6 |
7 |
8 | __all__ = ["Queue"]
9 |
10 |
11 | class Queue(Store):
12 | """
13 | This class represents the Queue store.
14 | Note that a Queue object isn't intended to be directly
15 | instantiated by the user.
16 | """
17 | def __init__(self, jinbase):
18 | """
19 | Init
20 |
21 | [params]
22 | - jinbase: Jinbase object
23 | """
24 | super().__init__(Model.QUEUE, jinbase)
25 |
26 | def enqueue(self, value):
27 | if value is None:
28 | return
29 | with self._dbc.immediate_transaction() as cursor:
30 | value = self._type_ref.adapt(value)
31 | datatype = misc.ensure_datatype(value, self._type_ref)
32 | if datatype is None:
33 | raise TypeError
34 | sql = queries.ENQUEUE
35 | db_timestamp = misc.get_timestamp(self._db_epoch, misc.now_dt(),
36 | self._timestamp_precision)
37 | cursor.execute(sql, (datatype.value, db_timestamp)) # write
38 | record_id = cursor.lastrowid
39 | self._store_data(record_id, datatype, value) # write
40 | return record_id
41 |
42 | def enqueue_many(self, values):
43 | with self._dbc.immediate_transaction() as cursor:
44 | uids = list()
45 | for value in values:
46 | uid = self.enqueue(value)
47 | uids.append(uid)
48 | return tuple(uids)
49 |
50 | def dequeue(self, default=None):
51 | with self._dbc.immediate_transaction() as cursor:
52 | r = self._get_front() # read
53 | if r is None: # nonexistent
54 | return default
55 | record_id, datatype, _ = r
56 | # get value
57 | value = self._retrieve_data(record_id, datatype) # read
58 | # delete record
59 | self._delete_record(record_id)
60 | return value
61 |
62 | def peek_front(self, default=None):
63 | with self._dbc.transaction():
64 | r = self._get_front() # read
65 | if r is None:
66 | return default
67 | record_id, datatype, _ = r
68 | return self._retrieve_data(record_id, datatype) # read
69 |
70 | def peek_back(self, default=None):
71 | with self._dbc.transaction():
72 | r = self._get_back() # read
73 | if r is None:
74 | return default
75 | record_id, datatype, _ = r
76 | return self._retrieve_data(record_id, datatype) # read
77 |
78 | def count_front_bytes(self):
79 | with self._dbc.transaction() as cur:
80 | r = self._get_front() # read
81 | if r is None:
82 | return 0
83 | record_id, _, _ = r
84 | sql = queries.COUNT_RECORD_BYTES.format(model=self._model_name)
85 | cur.execute(sql, (record_id,)) # read
86 | r = cur.fetchone()[0]
87 | return r if r else 0
88 |
89 | def count_back_bytes(self):
90 | with self._dbc.transaction() as cur:
91 | r = self._get_back() # read
92 | if r is None:
93 | return 0
94 | record_id, _, _ = r
95 | sql = queries.COUNT_RECORD_BYTES.format(model=self._model_name)
96 | cur.execute(sql, (record_id,)) # read
97 | r = cur.fetchone()[0]
98 | return r if r else 0
99 |
100 | def count_front_chunks(self):
101 | with self._dbc.transaction() as cur:
102 | r = self._get_front() # read
103 | if r is None:
104 | return 0
105 | record_id, _, _ = r
106 | sql = queries.COUNT_RECORD_CHUNKS.format(model=self._model_name)
107 | cur.execute(sql, (record_id,)) # read
108 | r = cur.fetchone()[0]
109 | return r if r else 0
110 |
111 | def count_back_chunks(self):
112 | with self._dbc.transaction() as cur:
113 | r = self._get_back() # read
114 | if r is None:
115 | return 0
116 | record_id, _, _ = r
117 | sql = queries.COUNT_RECORD_CHUNKS.format(model=self._model_name)
118 | cur.execute(sql, (record_id,)) # read
119 | r = cur.fetchone()[0]
120 | return r if r else 0
121 |
122 | def front_uid(self):
123 | with self._dbc.cursor() as cur:
124 | sql = queries.GET_QUEUE_FRONT_UID
125 | cur.execute(sql)
126 | r = cur.fetchone()
127 | if r is None:
128 | return
129 | return r[0]
130 |
131 | def back_uid(self):
132 | with self._dbc.cursor() as cur:
133 | sql = queries.GET_QUEUE_BACK_UID
134 | cur.execute(sql)
135 | r = cur.fetchone()
136 | if r is None:
137 | return
138 | return r[0]
139 |
140 | def info_front(self):
141 | r = self._get_front() # read
142 | if r is None:
143 | return
144 | record_id, datatype, db_timestamp = r
145 | created_at = misc.get_datetime_str(self._db_epoch, db_timestamp,
146 | self._timestamp_precision)
147 | return RecordInfo(uid=record_id, datatype=datatype, created_at=created_at)
148 |
149 | def info_back(self):
150 | r = self._get_back() # read
151 | if r is None:
152 | return
153 | record_id, datatype, db_timestamp = r
154 | created_at = misc.get_datetime_str(self._db_epoch, db_timestamp,
155 | self._timestamp_precision)
156 | return RecordInfo(uid=record_id, datatype=datatype, created_at=created_at)
157 |
158 | def _get_front(self):
159 | with self._dbc.cursor() as cur:
160 | sql = queries.GET_QUEUE_FRONT
161 | cur.execute(sql)
162 | r = cur.fetchone()
163 | if r is None:
164 | return
165 | record_id, dtype, db_timestamp = r
166 | return record_id, Datatype(dtype), db_timestamp
167 |
168 | def _get_back(self):
169 | with self._dbc.cursor() as cur:
170 | sql = queries.GET_QUEUE_BACK
171 | cur.execute(sql)
172 | r = cur.fetchone()
173 | if r is None:
174 | return
175 | record_id, dtype, db_timestamp = r
176 | return record_id, Datatype(dtype), db_timestamp
177 |
--------------------------------------------------------------------------------
/src/jinbase/store/stack.py:
--------------------------------------------------------------------------------
1 | """The Stack store is defined in this module."""
2 | from paradict import Datatype
3 | from jinbase import queries, misc
4 | from jinbase.const import Model
5 | from jinbase.store import Store, RecordInfo
6 |
7 |
8 | __all__ = ["Stack"]
9 |
10 |
11 | class Stack(Store):
12 | """
13 | This class represents the Stack store.
14 | Note that a Stack object isn't intended to be directly
15 | instantiated by the user.
16 | """
17 | def __init__(self, jinbase):
18 | """
19 | Init
20 |
21 | [params]
22 | - jinbase: Jinbase object
23 | """
24 | super().__init__(Model.STACK, jinbase)
25 |
26 | def push(self, value):
27 | if value is None:
28 | return
29 | with self._dbc.immediate_transaction() as cursor:
30 | value = self._type_ref.adapt(value)
31 | datatype = misc.ensure_datatype(value, self._type_ref)
32 | if datatype is None:
33 | raise TypeError
34 | sql = queries.STACK_PUSH
35 | db_timestamp = misc.get_timestamp(self._db_epoch, misc.now_dt(),
36 | self._timestamp_precision)
37 | cursor.execute(sql, (datatype.value, db_timestamp)) # write
38 | record_id = cursor.lastrowid
39 | self._store_data(record_id, datatype, value) # write
40 | return record_id
41 |
42 | def push_many(self, values):
43 | with self._dbc.immediate_transaction() as cursor:
44 | uids = list()
45 | for value in values:
46 | uid = self.push(value)
47 | uids.append(uid)
48 | return tuple(uids)
49 |
50 | def pop(self, default=None):
51 | with self._dbc.immediate_transaction() as cursor:
52 | r = self._get_top() # read
53 | if r is None:
54 | return default
55 | record_id, datatype, _ = r
56 | # get value
57 | value = self._retrieve_data(record_id, datatype) # read
58 | # delete record
59 | self._delete_record(record_id)
60 | return value
61 |
62 | def peek(self, default=None):
63 | with self._dbc.transaction():
64 | r = self._get_top() # read
65 | if r is None:
66 | return default
67 | record_id, datatype, _ = r
68 | return self._retrieve_data(record_id, datatype)
69 |
70 | def top_uid(self):
71 | with self._dbc.cursor() as cur:
72 | sql = queries.GET_STACK_TOP_UID
73 | cur.execute(sql)
74 | r = cur.fetchone()
75 | if r is None:
76 | return
77 | return r[0]
78 |
79 | def count_top_bytes(self):
80 | with self._dbc.transaction() as cur:
81 | r = self._get_top() # read
82 | if r is None:
83 | return 0
84 | record_id, _, _ = r
85 | sql = queries.COUNT_RECORD_BYTES.format(model=self._model_name)
86 | cur.execute(sql, (record_id,)) # read
87 | r = cur.fetchone()[0]
88 | return r if r else 0
89 |
90 | def count_top_chunks(self):
91 | with self._dbc.transaction() as cur:
92 | r = self._get_top() # read
93 | if r is None:
94 | return 0
95 | record_id, _, _ = r
96 | sql = queries.COUNT_RECORD_CHUNKS.format(model=self._model_name)
97 | cur.execute(sql, (record_id,)) # read
98 | r = cur.fetchone()[0]
99 | return r if r else 0
100 |
101 | def info_top(self):
102 | r = self._get_top() # read
103 | if r is None:
104 | return
105 | record_id, datatype, db_timestamp = r
106 | created_at = misc.get_datetime_str(self._db_epoch, db_timestamp,
107 | self._timestamp_precision)
108 | return RecordInfo(uid=record_id, datatype=datatype, created_at=created_at)
109 |
110 | def _get_top(self):
111 | with self._dbc.cursor() as cur:
112 | sql = queries.GET_STACK_TOP
113 | cur.execute(sql)
114 | r = cur.fetchone()
115 | if r is None:
116 | return
117 | record_id, dtype, db_timestamp = r
118 | return record_id, Datatype(dtype), db_timestamp
119 |
--------------------------------------------------------------------------------
/src/jinbase/transaction_policy.txt:
--------------------------------------------------------------------------------
1 | TRANSACTION POLICY
2 | ==================
3 |
4 | Use litedbc.LiteDBC.cursor context:
5 | - for a single Read
6 | - for a single Write
7 | - for a non-transactional sequence of Reads
8 | - for a non-transactional sequence of Writes
9 |
10 | Use litedbc.LiteDBC.transaction context:
11 | - for a transactional sequence of Reads
12 |
13 | Use litedbc.LiteDBC.immediate_transaction context:
14 | - for Read-then-Write
15 | - for a transactional sequence of Writes
16 |
--------------------------------------------------------------------------------
/tests/__init__.py:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/pyrustic/jinbase/baecf08698a39bd565c6938215e80cdbad910843/tests/__init__.py
--------------------------------------------------------------------------------
/tests/__main__.py:
--------------------------------------------------------------------------------
1 | import unittest
2 |
3 |
4 | def run_tests():
5 | test_loader = unittest.defaultTestLoader
6 | test_suite = test_loader.discover("tests", pattern="test_*.py")
7 | test_runner = unittest.TextTestRunner(verbosity=1)
8 | test_runner.run(test_suite)
9 |
10 |
11 | if __name__ == "__main__":
12 | run_tests()
13 |
--------------------------------------------------------------------------------
/tests/test_blob.py:
--------------------------------------------------------------------------------
1 | import os
2 | import unittest
3 | from jinbase.blob import get_blob_slices, update_position
4 |
5 |
6 | class TestGetBlobSlicesFunction(unittest.TestCase):
7 | """
8 | 1 2 3 4 5
9 | 0 1 2 3 4 0 1 2 3 4 0 1 2 3 4 0 1 2 3 4 0 1 2 3 4
10 | """
11 | def test(self):
12 | chunk_size = 5
13 | with self.subTest():
14 | start_index, stop_index = 0, 1
15 | r = get_blob_slices(start_index, stop_index, chunk_size)
16 | expected = ((0, slice(0, 2)),)
17 | self.assertEqual(expected, r)
18 | with self.subTest():
19 | start_index, stop_index = 0, 4
20 | r = get_blob_slices(start_index, stop_index, chunk_size)
21 | expected = ((0, slice(0, 5)),)
22 | self.assertEqual(expected, r)
23 | with self.subTest():
24 | start_index, stop_index = 0, 6
25 | r = get_blob_slices(start_index, stop_index, chunk_size)
26 | expected = ((0, slice(0, 5)),
27 | (1, slice(0, 2)))
28 | self.assertEqual(expected, r)
29 | with self.subTest():
30 | start_index, stop_index = 0, 13
31 | r = get_blob_slices(start_index, stop_index, chunk_size)
32 | expected = ((0, slice(0, 5)),
33 | (1, slice(0, 5)),
34 | (2, slice(0, 4)))
35 | self.assertEqual(expected, r)
36 | with self.subTest():
37 | start_index, stop_index = 6, 13
38 | r = get_blob_slices(start_index, stop_index, chunk_size)
39 | expected = ((1, slice(1, 5)),
40 | (2, slice(0, 4)))
41 | self.assertEqual(expected, r)
42 | with self.subTest():
43 | start_index, stop_index = 6, 18
44 | r = get_blob_slices(start_index, stop_index, chunk_size)
45 | expected = ((1, slice(1, 5)),
46 | (2, slice(0, 5)),
47 | (3, slice(0, 4)))
48 | self.assertEqual(expected, r)
49 |
50 | def test_start_equals_stop(self):
51 | chunk_size = 5
52 | with self.subTest():
53 | start_index, stop_index = 0, 0
54 | r = get_blob_slices(start_index, stop_index, chunk_size)
55 | expected = ((0, slice(0, 1)), )
56 | self.assertEqual(expected, r)
57 | with self.subTest():
58 | start_index, stop_index = 1, 1
59 | r = get_blob_slices(start_index, stop_index, chunk_size)
60 | expected = ((0, slice(1, 2)),)
61 | self.assertEqual(expected, r)
62 | with self.subTest():
63 | start_index, stop_index = 5, 5
64 | r = get_blob_slices(start_index, stop_index, chunk_size)
65 | expected = ((1, slice(0, 1)), )
66 | self.assertEqual(expected, r)
67 | with self.subTest():
68 | start_index, stop_index = 18, 18
69 | r = get_blob_slices(start_index, stop_index, chunk_size)
70 | expected = ((3, slice(3, 4)),)
71 | self.assertEqual(expected, r)
72 |
73 |
74 | class TestUpdatePositionFunction(unittest.TestCase):
75 |
76 | def test_with_seek_set_origin(self):
77 | n_bytes = 20
78 | with self.subTest("Offset equals 0"):
79 | cur_position = 5
80 | offset, origin = 0, os.SEEK_SET
81 | r = update_position(cur_position, offset, origin, n_bytes)
82 | expected = 0
83 | self.assertEqual(expected, r)
84 | with self.subTest("Offset is positive"):
85 | cur_position = 5
86 | offset, origin = 1, os.SEEK_SET
87 | r = update_position(cur_position, offset, origin, n_bytes)
88 | expected = 1
89 | self.assertEqual(expected, r)
90 | with self.subTest("Offset is negative"):
91 | cur_position = 5
92 | offset, origin = -1, os.SEEK_SET
93 | with self.assertRaises(ValueError):
94 | update_position(cur_position, offset, origin, n_bytes)
95 | with self.subTest("Offset to end of file"):
96 | cur_position = 5
97 | offset, origin = n_bytes, os.SEEK_SET
98 | r = update_position(cur_position, offset, origin, n_bytes)
99 | expected = n_bytes
100 | self.assertEqual(expected, r)
101 | with self.subTest("Offset is out of range"):
102 | cur_position = 5
103 | offset, origin = n_bytes+1, os.SEEK_SET
104 | with self.assertRaises(ValueError):
105 | update_position(cur_position, offset, origin, n_bytes)
106 |
107 | def test_with_seek_cur_origin(self):
108 | n_bytes = 20
109 | with self.subTest("Offset equals 0"):
110 | cur_position = 5
111 | offset, origin = 0, os.SEEK_CUR
112 | r = update_position(cur_position, offset, origin, n_bytes)
113 | expected = 5
114 | self.assertEqual(expected, r)
115 | with self.subTest("Offset is positive"):
116 | cur_position = 5
117 | offset, origin = 1, os.SEEK_CUR
118 | r = update_position(cur_position, offset, origin, n_bytes)
119 | expected = 6
120 | self.assertEqual(expected, r)
121 | with self.subTest("Offset is negative"):
122 | cur_position = 5
123 | offset, origin = -1, os.SEEK_CUR
124 | r = update_position(cur_position, offset, origin, n_bytes)
125 | expected = 4
126 | self.assertEqual(expected, r)
127 | with self.subTest("Offset to end of file"):
128 | cur_position = 5
129 | offset, origin = n_bytes - cur_position, os.SEEK_CUR
130 | r = update_position(cur_position, offset, origin, n_bytes)
131 | expected = n_bytes
132 | self.assertEqual(expected, r)
133 | with self.subTest("Offset is out of range"):
134 | cur_position = 5
135 | offset, origin = n_bytes - cur_position +1, os.SEEK_CUR
136 | with self.assertRaises(ValueError):
137 | update_position(cur_position, offset, origin, n_bytes)
138 |
139 | def test_with_seek_end_origin(self):
140 | n_bytes = 20
141 | with self.subTest("Offset equals 0"):
142 | cur_position = 5
143 | offset, origin = 0, os.SEEK_END # end of file
144 | r = update_position(cur_position, offset, origin, n_bytes)
145 | expected = n_bytes
146 | self.assertEqual(expected, r)
147 | with self.subTest("Offset is positive"):
148 | cur_position = 5
149 | offset, origin = 1, os.SEEK_END
150 | with self.assertRaises(ValueError):
151 | update_position(cur_position, offset, origin, n_bytes)
152 | with self.subTest("Offset is negative"):
153 | cur_position = 5
154 | offset, origin = -1, os.SEEK_END
155 | r = update_position(cur_position, offset, origin, n_bytes)
156 | expected = n_bytes - 1
157 | self.assertEqual(expected, r)
158 | with self.subTest("Offset to begin of file"):
159 | cur_position = 5
160 | offset, origin = -n_bytes, os.SEEK_END
161 | r = update_position(cur_position, offset, origin, n_bytes)
162 | expected = 0
163 | self.assertEqual(expected, r)
164 | with self.subTest("Offset is out of range"):
165 | cur_position = 5
166 | offset, origin = -n_bytes-1, os.SEEK_END
167 | with self.assertRaises(ValueError):
168 | update_position(cur_position, offset, origin, n_bytes)
169 |
170 |
171 | if __name__ == "__main__":
172 | unittest.main()
173 |
--------------------------------------------------------------------------------
/tests/test_imports.py:
--------------------------------------------------------------------------------
1 | import unittest
2 |
3 |
4 | class TestImports(unittest.TestCase):
5 |
6 | def test_import_classes(self):
7 | try:
8 | # import classes
9 | from jinbase import Jinbase
10 | from jinbase import TypeRef
11 | # import enums
12 | from jinbase import Model
13 | from jinbase import TimestampPrecision
14 | # import namedtuple
15 | from jinbase import RecordInfo
16 | # import consts
17 | from jinbase import TIMEOUT
18 | from jinbase import CHUNK_SIZE
19 | from jinbase import TIMESTAMP_PRECISION
20 | from jinbase import DATETIME_FORMAT
21 | from jinbase import USER_HOME
22 | from jinbase import JINBASE_HOME
23 | from jinbase import JINBASE_VERSION
24 | except ImportError:
25 | self.assertTrue(False)
26 |
27 |
28 | if __name__ == "__main__":
29 | unittest.main()
30 |
--------------------------------------------------------------------------------
/tests/test_jinbase.py:
--------------------------------------------------------------------------------
1 | import os.path
2 | import unittest
3 | import tempfile
4 | from datetime import datetime
5 | from litedbc import LiteDBC
6 | from jinbase import Jinbase, Model
7 | from jinbase.store.kv import Kv
8 | from jinbase.store.depot import Depot
9 | from jinbase.store.queue import Queue
10 | from jinbase.store.stack import Stack
11 |
12 |
13 | class TestEmptyJinbase(unittest.TestCase):
14 |
15 | def setUp(self):
16 | self._tempdir = tempfile.TemporaryDirectory()
17 | self._filename = os.path.join(self._tempdir.name, "my.db")
18 | self._jinbase = Jinbase(self._filename)
19 |
20 | def tearDown(self):
21 | self._jinbase.close()
22 | # the Try/Except is needed here because I can only
23 | # benefit from the constructor's "ignore_cleanup_errors=True"
24 | # in Python 3.10
25 | try:
26 | self._tempdir.cleanup()
27 | except Exception as e:
28 | pass
29 |
30 | def test_properties(self):
31 | with self.subTest("Test .filename property"):
32 | self.assertEqual(self._filename, self._jinbase.filename)
33 | with self.subTest("Test .is_new property"):
34 | self.assertTrue(self._jinbase.is_new)
35 | with self.subTest("Test .dbc property"):
36 | self.assertIsInstance(self._jinbase.dbc, LiteDBC)
37 | with self.subTest("Test .in_memory property"):
38 | self.assertFalse(self._jinbase.in_memory)
39 | with self.subTest("Test .version property"):
40 | self.assertEqual(1, self._jinbase.version)
41 | with self.subTest("Test .created_at property"):
42 | created_at = self._jinbase.created_at # ISO 8601 datetime string
43 | now = self._jinbase.now() # ISO 8601 datetime string
44 | self.assertGreaterEqual(datetime.fromisoformat(now),
45 | datetime.fromisoformat(created_at))
46 |
47 | def test_stores(self):
48 | with self.subTest("Test .kv property"):
49 | self.assertIsInstance(self._jinbase.kv, Kv)
50 | with self.subTest("Test .depot property"):
51 | self.assertIsInstance(self._jinbase.depot, Depot)
52 | with self.subTest("Test .queue property"):
53 | self.assertIsInstance(self._jinbase.queue, Queue)
54 | with self.subTest("Test .stack property"):
55 | self.assertIsInstance(self._jinbase.stack, Stack)
56 |
57 | def test_stats(self):
58 | with self.subTest("Test .count_records method"):
59 | self.assertEqual(0, self._jinbase.count_records())
60 | with self.subTest("Test .count_chunks method"):
61 | self.assertEqual(0, self._jinbase.count_chunks())
62 | with self.subTest("Test .count_bytes method"):
63 | self.assertEqual(0, self._jinbase.count_bytes())
64 |
65 | def test_scan_method(self):
66 | n_records = n_bytes = 0
67 | expected = {Model.KV: (n_records, n_bytes),
68 | Model.DEPOT: (n_records, n_bytes),
69 | Model.QUEUE: (n_records, n_bytes),
70 | Model.STACK: (n_records, n_bytes)}
71 | r = self._jinbase.scan()
72 | self.assertEqual(expected, self._jinbase.scan())
73 |
74 | def test_latest_method(self):
75 | user = {"id": 42, "name": "alex"}
76 | self._jinbase.kv.set("user", user)
77 | latest_write = self._jinbase.latest() # ISO 8601 datetime string
78 | now = self._jinbase.now_dt()
79 | self.assertGreaterEqual(now, datetime.fromisoformat(latest_write))
80 |
81 |
82 | class TestJinbaseControl(unittest.TestCase):
83 |
84 | def setUp(self):
85 | self._tempdir = tempfile.TemporaryDirectory()
86 | self._filename = os.path.join(self._tempdir.name, "my.db")
87 | self._jinbase = Jinbase(self._filename)
88 |
89 | def tearDown(self):
90 | self._jinbase.close()
91 | try:
92 | self._tempdir.cleanup()
93 | except Exception as e:
94 | pass
95 |
96 | def test_backup(self):
97 | kv_store = self._jinbase.kv
98 | user_data = {"id": 42, "name": "alex"}
99 | kv_store.set("user", user_data)
100 | dst_filename = os.path.join(self._tempdir.name, "backup.db")
101 | self._jinbase.backup(dst_filename)
102 | jinbase2 = Jinbase(dst_filename)
103 | kv_store2 = jinbase2.kv
104 | self.assertEqual(user_data, kv_store2.get("user"))
105 |
106 | def test_vacuum_into(self):
107 | kv_store = self._jinbase.kv
108 | user_data = {"id": 42, "name": "alex"}
109 | kv_store.set("user", user_data)
110 | dst_filename = os.path.join(self._tempdir.name, "backup.db")
111 | self._jinbase.vacuum_into(dst_filename)
112 | jinbase2 = Jinbase(dst_filename)
113 | kv_store2 = jinbase2.kv
114 | self.assertEqual(user_data, kv_store2.get("user"))
115 |
116 | def test_close(self):
117 | self._jinbase.close()
118 | self.assertTrue(os.path.isfile(self._filename))
119 | with self.assertRaises(Exception):
120 | self._jinbase.scan()
121 |
122 | def test_destroy(self):
123 | self._jinbase.destroy()
124 | self.assertFalse(os.path.isfile(self._filename))
125 | with self.assertRaises(Exception):
126 | self._jinbase.scan()
127 |
128 |
129 | class TestMultipleJinbaseConnections(unittest.TestCase):
130 |
131 | def setUp(self):
132 | self._tempdir = tempfile.TemporaryDirectory()
133 | self._filename = os.path.join(self._tempdir.name, "my.db")
134 | self._jinbase = Jinbase(self._filename)
135 |
136 | def tearDown(self):
137 | self._jinbase.close()
138 | try:
139 | self._tempdir.cleanup()
140 | except Exception as e:
141 | pass
142 |
143 | def test_copy_method(self):
144 | user_data1 = {"id": 42, "name": "alex"}
145 | user_data2 = {"id": 420}
146 | # jinbase1 get kv store then store item1
147 | kv_store = self._jinbase.kv
148 | kv_store.set("user1", user_data1)
149 | # jinbase2 accesses kv store then read item1
150 | jinbase2 = self._jinbase.copy()
151 | kv_store2 = jinbase2.kv
152 | self.assertEqual(user_data1, kv_store2.get("user1"))
153 | # jinbase2 stores item2 in kv store
154 | kv_store2.set("user2", user_data2)
155 | # jinbase1 reads item2
156 | self.assertEqual(user_data2, kv_store.get("user2"))
157 |
158 |
159 | class TestReadonlyJinbase(unittest.TestCase):
160 |
161 | def setUp(self):
162 | self._tempdir = tempfile.TemporaryDirectory()
163 | self._filename = os.path.join(self._tempdir.name, "my.db")
164 | self._jinbase = Jinbase(self._filename)
165 |
166 | def tearDown(self):
167 | self._jinbase.close()
168 | try:
169 | self._tempdir.cleanup()
170 | except Exception as e:
171 | pass
172 |
173 | def test(self):
174 | user_data = {"id": 42, "name": "alex"}
175 | kv_store = self._jinbase.kv
176 | with self.subTest("Readonly: False"):
177 | kv_store.set("user", user_data)
178 | self.assertEqual(user_data, kv_store.get("user"))
179 | with self.subTest("Readonly: True"):
180 | jinbase2 = Jinbase(self._filename, is_readonly=True)
181 | kv_store2 = jinbase2.kv
182 | self.assertEqual(user_data, kv_store2.get("user"))
183 | with self.assertRaises(Exception):
184 | kv_store2.set("user2", {"id": 420})
185 |
186 |
187 | class TestJinbaseContextManager(unittest.TestCase):
188 |
189 | def setUp(self):
190 | self._tempdir = tempfile.TemporaryDirectory()
191 | self._filename = os.path.join(self._tempdir.name, "my.db")
192 |
193 | def tearDown(self):
194 | try:
195 | self._tempdir.cleanup()
196 | except Exception as e:
197 | pass
198 |
199 | def test(self):
200 | with Jinbase(self._filename) as jinbase:
201 | pass
202 | self.assertTrue(jinbase.is_closed)
203 |
204 |
205 | class TestTransactionContext(unittest.TestCase):
206 |
207 | def setUp(self):
208 | self._tempdir = tempfile.TemporaryDirectory()
209 | self._filename = os.path.join(self._tempdir.name, "my.db")
210 | self._jinbase = Jinbase(self._filename)
211 |
212 | def tearDown(self):
213 | self._jinbase.close()
214 | try:
215 | self._tempdir.cleanup()
216 | except Exception as e:
217 | pass
218 |
219 | def test(self):
220 | kv_store = self._jinbase.kv
221 | depot_store = self._jinbase.depot
222 | queue_store = self._jinbase.queue
223 | stack_store = self._jinbase.stack
224 | with self._jinbase.transaction(): # TransactionMode.IMMEDIATE by default
225 | kv_store.set("user", 42)
226 | depot_store.append(42)
227 | queue_store.enqueue(42)
228 | stack_store.push(42)
229 |
230 |
231 | if __name__ == "__main__":
232 | unittest.main()
233 |
--------------------------------------------------------------------------------
/tests/test_misc.py:
--------------------------------------------------------------------------------
1 | import unittest
2 | from jinbase import misc
3 |
4 |
5 | if __name__ == "__main__":
6 | unittest.main()
7 |
--------------------------------------------------------------------------------
/tests/test_stack.py:
--------------------------------------------------------------------------------
1 | import os.path
2 | import unittest
3 | import tempfile
4 | import paradict
5 | from datetime import datetime
6 | from paradict import Datatype
7 | from jinbase import Jinbase, RecordInfo, const
8 |
9 |
10 | USER_CARD = {"id": 42, "name": "alex", "pi": 3.14,
11 | "photo": b'avatar.png', "permission": None,
12 | "birthday": datetime(2042, 12, 25,
13 | 16, 20, 59, 420),
14 | "books": {"sci_fi": ["Dune",
15 | "Neuromancer"],
16 | "romance": ["Happy Place",
17 | "Romantic Comedy"]}}
18 | EMPTY_USER_CARD = dict()
19 |
20 |
21 | class TestStackStore(unittest.TestCase):
22 |
23 | def setUp(self):
24 | self._tempdir = tempfile.TemporaryDirectory()
25 | self._filename = os.path.join(self._tempdir.name, "my.db")
26 | self._jinbase = Jinbase(self._filename)
27 | self._store = self._jinbase.stack
28 |
29 | def tearDown(self):
30 | try:
31 | self._tempdir.cleanup()
32 | except Exception as e:
33 | pass
34 |
35 | def test_info_top_method(self):
36 | with self.subTest("Non existent record"):
37 | self.assertIsNone(self._store.info_top())
38 | self._store.push("hello world")
39 | self._store.push(USER_CARD)
40 | with self.subTest("Existent record"):
41 | info = self._store.info_top()
42 | self.assertIsInstance(info, RecordInfo)
43 | self.assertEqual(Datatype.DICT, info.datatype)
44 | self.assertGreaterEqual(datetime.fromisoformat(self._store.now()),
45 | datetime.fromisoformat(info.created_at))
46 |
47 | def test_count_records_method(self):
48 | with self.subTest("Test that new store is empty"):
49 | self.assertEqual(0, self._store.count_records())
50 | with self.subTest("Test that store contains 1 item"):
51 | self._store.push(USER_CARD)
52 | self.assertEqual(1, self._store.count_records())
53 |
54 | def test_count_bytes_method(self):
55 | size_of_user = len(paradict.pack(USER_CARD))
56 | # set data
57 | self._store.push(USER_CARD)
58 | self._store.push(USER_CARD)
59 | # count bytes in the store
60 | with self.subTest():
61 | r = self._store.count_bytes()
62 | expected = size_of_user * 2
63 | self.assertEqual(expected, r)
64 |
65 | def test_count_top_bytes_method(self):
66 | size_of_user = len(paradict.pack(USER_CARD))
67 | # set data
68 | self._store.push(USER_CARD)
69 | self._store.push(USER_CARD)
70 | # count bytes of the item on top
71 | with self.subTest():
72 | r = self._store.count_top_bytes()
73 | expected = size_of_user
74 | self.assertEqual(expected, r)
75 |
76 | def test_is_empty(self):
77 | # ---
78 | with self.subTest("Test that new store is empty"):
79 | self.assertTrue(self._store.is_empty())
80 | # ---
81 | with self.subTest("Test that new store is not empty"):
82 | self._store.push(USER_CARD)
83 | self.assertFalse(self._store.is_empty())
84 |
85 | def test_push_method(self):
86 | with self.subTest("Test empty stack store"):
87 | self.assertEqual(0, self._store.count_records())
88 | with self.subTest("Test stack store after populating it"):
89 | self._store.push(USER_CARD)
90 | self.assertEqual(1, self._store.count_records())
91 | self._store.push(EMPTY_USER_CARD)
92 | self.assertEqual(2, self._store.count_records())
93 |
94 | def test_push_many_method(self):
95 | r = self._store.push_many((10, 11, 12, 13))
96 | expected = (1, 2, 3, 4)
97 | self.assertEqual(expected, r)
98 | self.assertEqual(4, self._store.count_records())
99 |
100 | def test_pop_method(self):
101 | with self.subTest("Test empty stack store"):
102 | self.assertIsNone(self._store.pop())
103 | with self.subTest("Test empty stack store with default value on"):
104 | self.assertEqual(USER_CARD, self._store.pop(default=USER_CARD))
105 | with self.subTest("Test stack store after populating it"):
106 | self._store.push(EMPTY_USER_CARD)
107 | self._store.push(USER_CARD)
108 | self.assertEqual(2, self._store.count_records())
109 | self.assertEqual(USER_CARD, self._store.pop())
110 | self.assertEqual(1, self._store.count_records())
111 | self.assertEqual(EMPTY_USER_CARD, self._store.pop())
112 | self.assertEqual(0, self._store.count_records())
113 |
114 | def test_peek_method(self):
115 | with self.subTest("Test empty stack store"):
116 | self.assertIsNone(self._store.peek())
117 | with self.subTest("Test empty stack store with default value on"):
118 | self.assertEqual(USER_CARD, self._store.peek(default=USER_CARD))
119 | with self.subTest("Test stack store after populating it"):
120 | self._store.push(EMPTY_USER_CARD)
121 | self._store.push(USER_CARD)
122 | self.assertEqual(USER_CARD, self._store.peek())
123 | self._store.pop()
124 | self.assertEqual(EMPTY_USER_CARD, self._store.peek())
125 |
126 | def test_get_top_rowid(self):
127 | rowid1 = self._store.push(USER_CARD)
128 | rowid2 = self._store.push(USER_CARD)
129 | self.assertEqual(rowid2, self._store.top_uid())
130 |
131 |
132 | class TestSmallestChunkSize(unittest.TestCase):
133 |
134 | def setUp(self):
135 | self._tempdir = tempfile.TemporaryDirectory()
136 | self._filename = os.path.join(self._tempdir.name, "my.db")
137 | smallest_chunk_size = 1
138 | self._jinbase = Jinbase(self._filename,
139 | chunk_size=smallest_chunk_size)
140 | self._store = self._jinbase.stack
141 |
142 | def tearDown(self):
143 | self._jinbase.close()
144 | try:
145 | self._tempdir.cleanup()
146 | except Exception as e:
147 | pass
148 |
149 | def test(self):
150 | with self.subTest("Test empty stack store"):
151 | self.assertEqual(0, self._store.count_records())
152 | with self.subTest("Test stack store after populating it"):
153 | self._store.push(USER_CARD)
154 | self.assertEqual(1, self._store.count_records())
155 | self._store.push(EMPTY_USER_CARD)
156 | self.assertEqual(2, self._store.count_records())
157 | with self.subTest("Test pop"):
158 | r = self._store.pop()
159 | self.assertEqual(EMPTY_USER_CARD, r)
160 | self.assertEqual(1, self._store.count_records())
161 | r = self._store.pop()
162 | self.assertEqual(USER_CARD, r)
163 | self.assertEqual(0, self._store.count_records())
164 |
165 | def test_count_top_chunks_method(self):
166 | self._store.push(EMPTY_USER_CARD)
167 | self._store.push(USER_CARD)
168 | size_user_card = len(paradict.pack(USER_CARD)) # n bytes
169 | size_empty_user_card = len(paradict.pack(EMPTY_USER_CARD)) # n bytes
170 | # count total chunks
171 | with self.subTest("Count total chunks"):
172 | n_chunks = self._store.count_chunks()
173 | expected_n_chunks = size_user_card + size_empty_user_card
174 | self.assertEqual(expected_n_chunks, n_chunks)
175 | # count front chunks
176 | with self.subTest("Count chunks at top"):
177 | n_chunks = self._store.count_top_chunks()
178 | expected_n_chunks = size_user_card
179 | self.assertEqual(expected_n_chunks, n_chunks)
180 | # pop then count total chunks
181 | with self.subTest("Pop then count total chunks"):
182 | self._store.pop()
183 | n_chunks = self._store.count_chunks()
184 | expected_n_chunks = size_empty_user_card
185 | self.assertEqual(expected_n_chunks, n_chunks)
186 |
187 |
188 | class TestDefaultValue(unittest.TestCase):
189 |
190 | def setUp(self):
191 | self._tempdir = tempfile.TemporaryDirectory()
192 | self._filename = os.path.join(self._tempdir.name, "my.db")
193 | smallest_chunk_size = 1 # 1 byte
194 | self._jinbase = Jinbase(self._filename,
195 | chunk_size=smallest_chunk_size)
196 | self._store = self._jinbase.stack
197 |
198 | def tearDown(self):
199 | self._jinbase.close()
200 | try:
201 | self._tempdir.cleanup()
202 | except Exception as e:
203 | pass
204 |
205 | def test(self):
206 | self.assertEqual(USER_CARD, self._store.pop(default=USER_CARD))
207 | self.assertEqual(USER_CARD, self._store.peek(default=USER_CARD))
208 |
209 |
210 | class TestTransactionContext(unittest.TestCase):
211 |
212 | def setUp(self):
213 | self._tempdir = tempfile.TemporaryDirectory()
214 | self._filename = os.path.join(self._tempdir.name, "my.db")
215 | self._jinbase = Jinbase(self._filename)
216 | self._store = self._jinbase.stack
217 |
218 | def tearDown(self):
219 | self._jinbase.close()
220 | try:
221 | self._tempdir.cleanup()
222 | except Exception as e:
223 | pass
224 |
225 | def test(self):
226 | with self._store.transaction(): # TransactionMode.IMMEDIATE by default
227 | self._store.push(USER_CARD)
228 | self._store.push(USER_CARD)
229 | self._store.pop()
230 |
231 |
232 | class TestLargeBinaryData(unittest.TestCase):
233 |
234 | def setUp(self):
235 | self._tempdir = tempfile.TemporaryDirectory()
236 | self._filename = os.path.join(self._tempdir.name, "my.db")
237 | self._jinbase = Jinbase(self._filename)
238 | self._store = self._jinbase.stack
239 |
240 | def tearDown(self):
241 | self._jinbase.close()
242 | try:
243 | self._tempdir.cleanup()
244 | except Exception as e:
245 | pass
246 |
247 | def test(self):
248 | data = b'\x00' * (const.CHUNK_SIZE * 2)
249 | self._store.push(data)
250 | self.assertEqual(data, self._store.pop())
251 |
252 |
253 | if __name__ == "__main__":
254 | unittest.main()
255 |
--------------------------------------------------------------------------------