deepfos 1.1.24__tar.gz → 1.1.25__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (181) hide show
  1. {deepfos-1.1.24 → deepfos-1.1.25}/PKG-INFO +1 -1
  2. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/_version.py +3 -3
  3. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/financial_model.py +2 -0
  4. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/finmodel.py +105 -21
  5. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/exceptions/__init__.py +4 -0
  6. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/asynchronous.py +49 -23
  7. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/serutils.py +4 -20
  8. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos.egg-info/PKG-INFO +1 -1
  9. {deepfos-1.1.24 → deepfos-1.1.25}/MANIFEST.in +0 -0
  10. {deepfos-1.1.24 → deepfos-1.1.25}/README.md +0 -0
  11. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/__init__.py +0 -0
  12. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/algo/__init__.py +0 -0
  13. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/algo/graph.py +0 -0
  14. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/V1_1/__init__.py +0 -0
  15. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/V1_1/business_model.py +0 -0
  16. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/V1_1/dimension.py +0 -0
  17. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/V1_1/models/__init__.py +0 -0
  18. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/V1_1/models/business_model.py +0 -0
  19. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/V1_1/models/dimension.py +0 -0
  20. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/V1_2/__init__.py +0 -0
  21. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/V1_2/dimension.py +0 -0
  22. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/V1_2/models/__init__.py +0 -0
  23. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/V1_2/models/dimension.py +0 -0
  24. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/__init__.py +0 -0
  25. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/account.py +0 -0
  26. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/accounting_engines.py +0 -0
  27. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/app.py +0 -0
  28. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/approval_process.py +0 -0
  29. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/base.py +0 -0
  30. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/business_model.py +0 -0
  31. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/consolidation.py +0 -0
  32. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/consolidation_process.py +0 -0
  33. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/datatable.py +0 -0
  34. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/deepconnector.py +0 -0
  35. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/deepfos_task.py +0 -0
  36. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/deepmodel.py +0 -0
  37. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/dimension.py +0 -0
  38. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/financial_model.py +0 -0
  39. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/journal_model.py +0 -0
  40. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/journal_template.py +0 -0
  41. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/memory_financial_model.py +0 -0
  42. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/__init__.py +0 -0
  43. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/account.py +0 -0
  44. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/accounting_engines.py +0 -0
  45. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/app.py +0 -0
  46. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/approval_process.py +0 -0
  47. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/base.py +0 -0
  48. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/business_model.py +0 -0
  49. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/consolidation.py +0 -0
  50. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/consolidation_process.py +0 -0
  51. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/datatable_mysql.py +0 -0
  52. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/deepconnector.py +0 -0
  53. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/deepfos_task.py +0 -0
  54. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/deepmodel.py +0 -0
  55. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/dimension.py +0 -0
  56. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/journal_model.py +0 -0
  57. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/journal_template.py +0 -0
  58. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/memory_financial_model.py +0 -0
  59. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/platform.py +0 -0
  60. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/python.py +0 -0
  61. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/reconciliation_engine.py +0 -0
  62. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/reconciliation_report.py +0 -0
  63. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/role_strategy.py +0 -0
  64. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/smartlist.py +0 -0
  65. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/space.py +0 -0
  66. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/system.py +0 -0
  67. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/variable.py +0 -0
  68. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/models/workflow.py +0 -0
  69. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/platform.py +0 -0
  70. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/python.py +0 -0
  71. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/reconciliation_engine.py +0 -0
  72. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/reconciliation_report.py +0 -0
  73. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/role_strategy.py +0 -0
  74. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/smartlist.py +0 -0
  75. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/space.py +0 -0
  76. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/system.py +0 -0
  77. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/variable.py +0 -0
  78. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/api/workflow.py +0 -0
  79. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/boost/__init__.py +0 -0
  80. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/boost/jstream.c +0 -0
  81. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/boost/jstream.pyx +0 -0
  82. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/boost/pandas.c +0 -0
  83. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/boost/pandas.pyx +0 -0
  84. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/boost/py_jstream.py +0 -0
  85. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/boost/py_pandas.py +0 -0
  86. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/cache.py +0 -0
  87. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/config.py +0 -0
  88. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/__init__.py +0 -0
  89. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/cube/__init__.py +0 -0
  90. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/cube/_base.py +0 -0
  91. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/cube/constants.py +0 -0
  92. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/cube/cube.py +0 -0
  93. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/cube/formula.py +0 -0
  94. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/cube/syscube.py +0 -0
  95. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/cube/typing.py +0 -0
  96. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/cube/utils.py +0 -0
  97. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/dimension/__init__.py +0 -0
  98. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/dimension/_base.py +0 -0
  99. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/dimension/dimcreator.py +0 -0
  100. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/dimension/dimension.py +0 -0
  101. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/dimension/dimexpr.py +0 -0
  102. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/dimension/dimmember.py +0 -0
  103. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/dimension/eledimension.py +0 -0
  104. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/dimension/filters.py +0 -0
  105. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/dimension/sysdimension.py +0 -0
  106. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/logictable/__init__.py +0 -0
  107. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/logictable/_cache.py +0 -0
  108. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/logictable/_operator.py +0 -0
  109. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/logictable/nodemixin.py +0 -0
  110. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/logictable/sqlcondition.py +0 -0
  111. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/core/logictable/tablemodel.py +0 -0
  112. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/__init__.py +0 -0
  113. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/cipher.py +0 -0
  114. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/clickhouse.py +0 -0
  115. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/connector.py +0 -0
  116. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/daclickhouse.py +0 -0
  117. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/dameng.py +0 -0
  118. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/damysql.py +0 -0
  119. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/dbkits.py +0 -0
  120. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/deepengine.py +0 -0
  121. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/deepmodel.py +0 -0
  122. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/deepmodel_kingbase.py +0 -0
  123. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/edb.py +0 -0
  124. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/gauss.py +0 -0
  125. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/kingbase.py +0 -0
  126. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/mysql.py +0 -0
  127. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/oracle.py +0 -0
  128. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/postgresql.py +0 -0
  129. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/sqlserver.py +0 -0
  130. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/db/utils.py +0 -0
  131. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/__init__.py +0 -0
  132. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/accounting.py +0 -0
  133. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/apvlprocess.py +0 -0
  134. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/base.py +0 -0
  135. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/bizmodel.py +0 -0
  136. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/datatable.py +0 -0
  137. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/deepconnector.py +0 -0
  138. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/deepmodel.py +0 -0
  139. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/dimension.py +0 -0
  140. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/fact_table.py +0 -0
  141. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/journal.py +0 -0
  142. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/journal_template.py +0 -0
  143. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/pyscript.py +0 -0
  144. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/reconciliation.py +0 -0
  145. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/rolestrategy.py +0 -0
  146. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/smartlist.py +0 -0
  147. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/variable.py +0 -0
  148. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/element/workflow.py +0 -0
  149. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/exceptions/hook.py +0 -0
  150. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lazy.py +0 -0
  151. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/__init__.py +0 -0
  152. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/_javaobj.py +0 -0
  153. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/concurrency.py +0 -0
  154. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/constant.py +0 -0
  155. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/decorator.py +0 -0
  156. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/deepchart.py +0 -0
  157. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/deepux.py +0 -0
  158. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/discovery.py +0 -0
  159. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/eureka.py +0 -0
  160. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/filterparser.py +0 -0
  161. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/httpcli.py +0 -0
  162. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/jsonstreamer.py +0 -0
  163. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/nacos.py +0 -0
  164. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/patch.py +0 -0
  165. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/redis.py +0 -0
  166. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/stopwatch.py +0 -0
  167. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/subtask.py +0 -0
  168. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/sysutils.py +0 -0
  169. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/lib/utils.py +0 -0
  170. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/local.py +0 -0
  171. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/options.py +0 -0
  172. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos/translation.py +0 -0
  173. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos.egg-info/SOURCES.txt +0 -0
  174. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos.egg-info/dependency_links.txt +0 -0
  175. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos.egg-info/not-zip-safe +0 -0
  176. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos.egg-info/requires.txt +0 -0
  177. {deepfos-1.1.24 → deepfos-1.1.25}/deepfos.egg-info/top_level.txt +0 -0
  178. {deepfos-1.1.24 → deepfos-1.1.25}/setup.cfg +0 -0
  179. {deepfos-1.1.24 → deepfos-1.1.25}/setup.py +0 -0
  180. {deepfos-1.1.24 → deepfos-1.1.25}/tests/__init__.py +0 -0
  181. {deepfos-1.1.24 → deepfos-1.1.25}/versioneer.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: deepfos
3
- Version: 1.1.24
3
+ Version: 1.1.25
4
4
  Summary: Collecions of useful and handy tools for deepfos platform
5
5
  Home-page: http://py.deepfos.com
6
6
  Author: deepfos-python-team
@@ -8,11 +8,11 @@ import json
8
8
 
9
9
  version_json = '''
10
10
  {
11
- "date": "2023-12-12T03:45:14+0000",
11
+ "date": "2023-12-19T06:52:40+0000",
12
12
  "dirty": false,
13
13
  "error": null,
14
- "full-revisionid": "c206dc5e4a3d9eb870bc032b55c17276ea7d9322",
15
- "version": "1.1.24"
14
+ "full-revisionid": "0c1304879b006d56f7565a69c2cb418cd6f94968",
15
+ "version": "1.1.25"
16
16
  }
17
17
  ''' # END VERSION_JSON
18
18
 
@@ -1159,6 +1159,8 @@ class ReactSpreadsheetSaveForm(BaseModel):
1159
1159
  wbName: Optional[str]
1160
1160
  #: 电子表格path
1161
1161
  wbPath: Optional[str]
1162
+ #: 是否回调
1163
+ callback: Optional[bool]
1162
1164
 
1163
1165
 
1164
1166
  class SheetColumnDto(BaseModel):
@@ -44,8 +44,7 @@ from deepfos.api.models.financial_model import (
44
44
  from deepfos.api.models.base import BaseModel
45
45
  from deepfos.options import OPTION
46
46
  from deepfos.lib.decorator import cached_property
47
- from deepfos.exceptions import MDXExecuteTimeout
48
-
47
+ from deepfos.exceptions import MDXExecuteTimeout, MDXExecuteFail
49
48
 
50
49
  __all__ = [
51
50
  'AsyncFinancialCube',
@@ -487,6 +486,7 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
487
486
  need_check: bool = True,
488
487
  data_audit: bool = True,
489
488
  chunksize: Optional[int] = None,
489
+ callback: bool = True
490
490
  ):
491
491
  """
492
492
  将DataFrame的数据保存至cube。
@@ -499,6 +499,7 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
499
499
  data_audit: 是否需要记录到数据审计
500
500
  chunksize: 单次调用保存接口时最大的dataframe行数。
501
501
  当data的行数超过此值时,将会分多次进行保存。
502
+ callback: 是否回调
502
503
 
503
504
  Note:
504
505
  此方法会对落库数据做以下处理:
@@ -539,7 +540,10 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
539
540
  if missing_dims := required_cols - set(data.columns):
540
541
  raise ValueError(
541
542
  f"Cannot save data because following columns are missing: {missing_dims}")
542
- return await self._save_impl(data[list(required_cols)], pov, need_check, data_audit, chunksize)
543
+ return await self._save_impl(
544
+ data[list(required_cols)],
545
+ pov, need_check, data_audit, chunksize, callback
546
+ )
543
547
 
544
548
  async def save_unpivot(
545
549
  self,
@@ -550,6 +554,7 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
550
554
  data_audit: bool = True,
551
555
  chunksize: Optional[int] = None,
552
556
  save_nan: bool = False,
557
+ callback: bool = True
553
558
  ):
554
559
  """保存有某个维度所有成员在列上的 ``DataFrame``
555
560
 
@@ -567,6 +572,7 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
567
572
  chunksize: 单次调用保存接口时最大的dataframe行数。
568
573
  当data的行数超过此值时,将会分多次进行保存。
569
574
  save_nan: 当把数据列成员转换到行上时,data为空的数据是否保存
575
+ callback: 是否回调
570
576
 
571
577
  Warnings:
572
578
  由于数据完整性等原因,此方法接收的dataframe数据列经常会有一些额外的空值。
@@ -610,7 +616,9 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
610
616
  logger.info("Will not save to cube because dataframe is empty.")
611
617
  return
612
618
 
613
- return await self._save_impl(data, pov, need_check, data_audit, chunksize)
619
+ return await self._save_impl(
620
+ data, pov, need_check, data_audit, chunksize, callback
621
+ )
614
622
 
615
623
  async def _save_impl(
616
624
  self,
@@ -619,6 +627,7 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
619
627
  need_check: bool = True,
620
628
  data_audit: bool = True,
621
629
  chunksize: Optional[int] = None,
630
+ callback: bool = True
622
631
  ):
623
632
  # replace NaN to standard None
624
633
  data = data.mask(data.isna(), None)
@@ -643,18 +652,20 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
643
652
  needCheck=need_check,
644
653
  dataAuditSwitch=data_audit,
645
654
  entryMode=1,
646
- validateDimensionMember=need_check
655
+ validateDimensionMember=need_check,
656
+ callback=callback
657
+ )
658
+ r = await self.async_api.reactspreadsheet.save(
659
+ payload.dict(exclude_unset=True)
647
660
  )
648
- r = await self.async_api.reactspreadsheet.save(payload.dict(exclude_unset=True))
649
661
  resp.append(r)
650
662
  return resp
651
663
 
652
- async def delete(
664
+ async def delete_with_mdx(
653
665
  self,
654
- expression: Union[str, Dict[str, Union[List[str], str]]],
655
- chunksize: Optional[int] = None
666
+ expression: Union[str, Dict[str, Union[List[str], str]]]
656
667
  ):
657
- """删除数据
668
+ """通过MDX脚本删除数据
658
669
 
659
670
  根据维度表达式删除Cube数据
660
671
 
@@ -665,7 +676,6 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
665
676
 
666
677
  Args:
667
678
  expression: 维度表达式
668
- chunksize: 目前使用MDX实现,已弃用(弃用版本: 1.1.24),仅兼容旧版本保留
669
679
 
670
680
  .. admonition:: 示例
671
681
 
@@ -676,25 +686,20 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
676
686
 
677
687
  cube = FinancialCube('example')
678
688
  expr = 'Year{2021;2022}->Entiy{Base(TotalEntity,0)}'
679
- r = cube.delete(expr)
689
+ r = cube.delete_with_mdx(expr)
680
690
  expr_dict = {
681
691
  "Year": ['2021', '2022'],
682
692
  "Entity": "Base(TotalEntity,0)"
683
693
  }
684
- r = cube.delete(expr_dict)
694
+ r = cube.delete_with_mdx(expr_dict)
685
695
 
686
696
  Returns:
687
- 删除结果
697
+ MDX执行结果
688
698
 
689
699
  See Also:
690
- :meth:`insert_null`
700
+ :meth:`insert_null` :meth:`delete`
691
701
 
692
702
  """
693
- if chunksize:
694
- logger.warning(
695
- 'Parameter \'chunksize\' is deprecated since 1.1.24'
696
- )
697
-
698
703
  if isinstance(expression, dict):
699
704
  expression = dict_to_expr(expression)
700
705
 
@@ -779,6 +784,69 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
779
784
 
780
785
  return await self.mdx_execution(script)
781
786
 
787
+ async def delete(
788
+ self,
789
+ expression: Union[str, Dict[str, Union[List[str], str]]],
790
+ chunksize: Optional[int] = None,
791
+ use_mdx: bool = False,
792
+ callback: bool = True
793
+ ):
794
+ """删除数据
795
+
796
+ 根据维度表达式删除Cube数据。
797
+
798
+ Warnings:
799
+ 此方法首先查询数据,并且替换为null再调用保存接口。
800
+ 因此如果要删除的数据量大,可能导致内存不足等问题。
801
+ 如果不需要数据审计功能,请使用 :meth:`insert_null`
802
+
803
+ Args:
804
+ expression: 维度表达式
805
+ chunksize: 单次调用保存接口时最大的dataframe行数。
806
+ 当data的行数超过此值时,将会分多次进行保存。
807
+ use_mdx: 是否使用MDX脚本实现,默认为否,等效于调用 :meth:`delete_with_mdx`
808
+ callback: 是否回调
809
+
810
+ .. admonition:: 示例
811
+
812
+ 两种调用方式等价:
813
+
814
+ .. code-block:: python
815
+ :emphasize-lines: 3,8
816
+
817
+ cube = FinancialCube('example')
818
+ expr = 'Year{2021;2022}->Entiy{Base(TotalEntity,0)}'
819
+ r = cube.delete(expr)
820
+ expr_dict = {
821
+ "Year": ['2021', '2022'],
822
+ "Entity": "Base(TotalEntity,0)"
823
+ }
824
+ r = cube.delete(expr_dict)
825
+
826
+ Returns:
827
+ 删除结果
828
+
829
+ See Also:
830
+ :meth:`insert_null` :meth:`delete_with_mdx`
831
+
832
+ """
833
+ if use_mdx:
834
+ return await self.delete_with_mdx(expression)
835
+
836
+ if self._meta.autoCalculation:
837
+ if isinstance(expression, str):
838
+ expression = expr_to_dict(expression)
839
+ expression = {**expression}
840
+
841
+ if isinstance(expression, dict):
842
+ expression = dict_to_expr(expression)
843
+
844
+ data, pov = await self.query(expression)
845
+ data[DFLT_DATA_COLUMN] = None
846
+ return await self.save(
847
+ data, pov, data_audit=True, chunksize=chunksize, callback=callback
848
+ )
849
+
782
850
  async def queries(
783
851
  self,
784
852
  expressions: Iterable[str],
@@ -1204,6 +1272,11 @@ class AsyncFinancialCube(ElementBase[FinancialModelAPI]):
1204
1272
  if res.status == 1:
1205
1273
  raise MDXExecuteTimeout(f'MDX执行超时,具体响应:\n{res}')
1206
1274
 
1275
+ if res.result is False:
1276
+ raise MDXExecuteFail(
1277
+ f'MDX执行失败,失败原因:\n{res.failReason}'
1278
+ )
1279
+
1207
1280
  return res
1208
1281
 
1209
1282
 
@@ -1214,6 +1287,7 @@ class FinancialCube(AsyncFinancialCube, metaclass=SyncMeta):
1214
1287
  'save',
1215
1288
  'save_unpivot',
1216
1289
  'delete',
1290
+ 'delete_with_mdx',
1217
1291
  'pc_init',
1218
1292
  'pc_update',
1219
1293
  'pc_upsert',
@@ -1252,6 +1326,7 @@ class FinancialCube(AsyncFinancialCube, metaclass=SyncMeta):
1252
1326
  need_check: bool = True,
1253
1327
  data_audit: bool = True,
1254
1328
  chunksize: Optional[int] = None,
1329
+ callback: bool = True
1255
1330
  ):
1256
1331
  ...
1257
1332
 
@@ -1264,13 +1339,22 @@ class FinancialCube(AsyncFinancialCube, metaclass=SyncMeta):
1264
1339
  data_audit: bool = True,
1265
1340
  chunksize: Optional[int] = None,
1266
1341
  save_nan: bool = False,
1342
+ callback: bool = True
1267
1343
  ):
1268
1344
  ...
1269
1345
 
1270
1346
  def delete(
1271
1347
  self,
1272
1348
  expression: Union[str, Dict[str, Union[List[str], str]]],
1273
- chunksize: Optional[int] = None
1349
+ chunksize: Optional[int] = None,
1350
+ use_mdx: bool = False,
1351
+ callback: bool = True
1352
+ ):
1353
+ ...
1354
+
1355
+ def delete_with_mdx(
1356
+ self,
1357
+ expression: Union[str, Dict[str, Union[List[str], str]]]
1274
1358
  ):
1275
1359
  ...
1276
1360
 
@@ -129,6 +129,10 @@ class MDXExecuteTimeout(DeepfosBaseException):
129
129
  """执行MDX任务超时"""
130
130
 
131
131
 
132
+ class MDXExecuteFail(DeepfosBaseException):
133
+ """执行MDX任务失败"""
134
+
135
+
132
136
  # -----------------------------------------------------------------------------
133
137
  # DeepModel Error
134
138
  class DeepModelError(DeepfosBaseException):
@@ -1,7 +1,10 @@
1
+ from __future__ import annotations
2
+
1
3
  import asyncio
2
4
  import itertools
3
5
  from asyncio import SelectorEventLoop
4
6
  import asyncio.events as events
7
+ from asyncio import Future as AioFuture
5
8
  import sys
6
9
  from contextlib import contextmanager
7
10
  from heapq import heappop
@@ -14,7 +17,7 @@ import atexit
14
17
  from typing import (
15
18
  Optional, Tuple, Union, TYPE_CHECKING, List,
16
19
  Callable, NamedTuple, Coroutine, Any, Dict,
17
- Generic, Iterable, TypeVar, Awaitable, overload
20
+ Generic, Iterable, TypeVar, Awaitable, overload,
18
21
  )
19
22
  # noinspection PyProtectedMember
20
23
  from concurrent.futures._base import (
@@ -269,11 +272,11 @@ class LinkedList(Generic[LinkListItem]):
269
272
  self.remove(node)
270
273
 
271
274
 
272
- class _AbstractTask(Generic[FutureT]):
275
+ class _AbstractTask(Generic[ReturnT]):
273
276
  def __init__(
274
277
  self,
275
- future: FutureT,
276
- coro: Coroutine,
278
+ future: Union[Future[ReturnT], AioFuture[ReturnT]],
279
+ coro: Coroutine[ReturnT, Any, ReturnT],
277
280
  ensure_completed: bool = False,
278
281
  die_in_peace: bool = False
279
282
  ):
@@ -282,10 +285,10 @@ class _AbstractTask(Generic[FutureT]):
282
285
  self.ensure_completed = ensure_completed
283
286
  self.die_in_peace = die_in_peace
284
287
 
285
- def result(self, timeout: Optional[float] = None): # pragma: no cover
288
+ def result(self, timeout: Optional[float] = None) -> ReturnT: # pragma: no cover
286
289
  raise NotImplementedError
287
290
 
288
- def done(self):
291
+ def done(self) -> bool:
289
292
  return self.future.done()
290
293
 
291
294
  def add_done_callback(self, callback):
@@ -305,26 +308,40 @@ class _AbstractTask(Generic[FutureT]):
305
308
  )
306
309
 
307
310
 
308
- class AsyncIOTask(_AbstractTask[asyncio.Future]):
309
- def __init__(self, future, coro, ensure):
310
- super().__init__(future, coro, ensure)
311
+ class AsyncIOTask(_AbstractTask):
312
+ def __init__(
313
+ self,
314
+ future: AioFuture[ReturnT],
315
+ coro: Coroutine[ReturnT, Any, ReturnT],
316
+ ensure_completed: bool = False,
317
+ ):
318
+ super().__init__(future, coro, ensure_completed)
311
319
  self.r = UNSET
320
+ self.exc = None
312
321
  self.future.add_done_callback(self.set_task_done)
313
322
 
314
- def set_task_done(self, future: asyncio.Future):
315
- self.r = future.result()
323
+ def set_task_done(self, future: AioFuture):
324
+ if exc := future.exception():
325
+ self.exc = exc
326
+ else:
327
+ self.r = future.result()
316
328
 
317
329
  async def _wait_for_result(self, timeout=None):
318
330
  return await asyncio.wait_for(self.future, timeout)
319
331
 
320
- def result(self, timeout: Optional[float] = None):
332
+ def result(self, timeout: Optional[float] = None) -> ReturnT:
333
+ if self.exc is not None:
334
+ raise self.exc
321
335
  if self.r is UNSET:
322
336
  evloop.run(self._wait_for_result(timeout))
323
337
  return self.r
324
338
 
325
339
 
326
- class ThreadTask(_AbstractTask[Future]):
327
- def result(self, timeout: Optional[float] = None):
340
+ class ThreadTask(_AbstractTask):
341
+ if TYPE_CHECKING:
342
+ future: Future
343
+
344
+ def result(self, timeout: Optional[float] = None) -> ReturnT:
328
345
  if (
329
346
  evloop.in_same_thread()
330
347
  and not (
@@ -419,13 +436,17 @@ class EventLoop:
419
436
  def set_loop(self, loop: asyncio.BaseEventLoop):
420
437
  self.__loop = loop
421
438
 
422
- def run(self, coro):
439
+ def run(self, coro: Coroutine[ReturnT, Any, ReturnT]) -> ReturnT:
423
440
  if self.in_same_thread():
424
441
  return self.loop.run_until_complete(coro)
425
442
  else:
426
443
  return self.create_task(coro).result()
427
444
 
428
- def create_task(self, coro, ensure_completed=False) -> _AbstractTask:
445
+ def create_task(
446
+ self,
447
+ coro: Coroutine[ReturnT, Any, ReturnT],
448
+ ensure_completed=False
449
+ ) -> _AbstractTask[ReturnT]:
429
450
  task: _AbstractTask
430
451
  if self.in_same_thread():
431
452
  task = AsyncIOTask(
@@ -446,7 +467,12 @@ class EventLoop:
446
467
 
447
468
  def _report_task_done(self, node: Node):
448
469
  def cb(fut):
449
- logger.debug(f"Task {node.value} finished.")
470
+ def get_hint():
471
+ if exc := fut.exception():
472
+ return f'failed with exception: {exc!r}'
473
+ else:
474
+ return f'finsihed with result: {fut.result()}'
475
+ logger.opt(lazy=True).debug(f"Task {node.value} {{}}", get_hint)
450
476
  self._tasks.remove(node)
451
477
  return cb
452
478
 
@@ -539,7 +565,7 @@ class EventLoop:
539
565
  periodic_task.task.cancel()
540
566
  if periodic_task.on_stop is not None:
541
567
  self.run(periodic_task.on_stop())
542
- except Exception: # pragma: no cover
568
+ except Exception: # pragma: no cover # noqa
543
569
  logger.exception("Exception occurs when cancel task.")
544
570
 
545
571
 
@@ -599,16 +625,16 @@ class _TaskProp:
599
625
  class future_property(Generic[ReturnT]):
600
626
  def __init__(
601
627
  self,
602
- func: Optional[Callable[[Any], Awaitable[ReturnT]]] = None,
603
- on_demand=False
628
+ func: Optional[Callable[[Any], Coroutine[ReturnT, Any, ReturnT]]] = None,
629
+ on_demand: bool = False
604
630
  ):
605
631
  self.func = func
606
632
  self.on_demand = on_demand
607
633
  if func is not None:
608
634
  self.__doc__ = func.__doc__
609
- self._tasks: Dict[Any, _TaskProp] = {}
635
+ self._tasks: Dict[int, _TaskProp] = {}
610
636
 
611
- def __call__(self, func: Callable[[Any], Awaitable[ReturnT]]):
637
+ def __call__(self, func: Callable[[Any], Coroutine[ReturnT, Any, ReturnT]]):
612
638
  self.func = func
613
639
  self.__doc__ = func.__doc__
614
640
  return self
@@ -778,7 +804,7 @@ class DeepFOSIO:
778
804
  finally:
779
805
  try:
780
806
  await self.apply_handler(self.on_shutdown)
781
- except Exception: # pragma: no cover
807
+ except Exception: # pragma: no cover # noqa
782
808
  pass
783
809
 
784
810
 
@@ -107,39 +107,23 @@ def _set(o):
107
107
  return [serialize(el) for el in o]
108
108
 
109
109
 
110
- @serialize.register(uuid.UUID)
111
- def _stringify(o):
112
- return str(o)
113
-
114
-
115
110
  @serialize.register(int)
116
111
  @serialize.register(float)
117
112
  @serialize.register(str)
118
113
  @serialize.register(bytes)
119
114
  @serialize.register(bool)
120
115
  @serialize.register(type(None))
116
+ @serialize.register(uuid.UUID)
121
117
  @serialize.register(decimal.Decimal)
122
118
  @serialize.register(datetime.timedelta)
119
+ @serialize.register(datetime.date)
120
+ @serialize.register(datetime.datetime)
121
+ @serialize.register(datetime.time)
123
122
  @serialize.register(edgedb.RelativeDuration)
124
123
  def _scalar(o):
125
124
  return o
126
125
 
127
126
 
128
- @serialize.register
129
- def _datetime(o: datetime.datetime):
130
- return o.isoformat()
131
-
132
-
133
- @serialize.register
134
- def _date(o: datetime.date):
135
- return o.isoformat()
136
-
137
-
138
- @serialize.register
139
- def _time(o: datetime.time):
140
- return o.isoformat()
141
-
142
-
143
127
  @serialize.register
144
128
  def _enum(o: edgedb.EnumValue):
145
129
  return str(o)
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: deepfos
3
- Version: 1.1.24
3
+ Version: 1.1.25
4
4
  Summary: Collecions of useful and handy tools for deepfos platform
5
5
  Home-page: http://py.deepfos.com
6
6
  Author: deepfos-python-team
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes