DIRAC 9.0.0a42__py3-none-any.whl → 9.0.7__py3-none-any.whl

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 (236) hide show
  1. DIRAC/AccountingSystem/Client/AccountingCLI.py +0 -140
  2. DIRAC/AccountingSystem/Client/DataStoreClient.py +0 -13
  3. DIRAC/AccountingSystem/Client/Types/BaseAccountingType.py +0 -7
  4. DIRAC/AccountingSystem/ConfigTemplate.cfg +0 -5
  5. DIRAC/AccountingSystem/Service/DataStoreHandler.py +0 -72
  6. DIRAC/ConfigurationSystem/Client/Helpers/CSGlobals.py +0 -9
  7. DIRAC/ConfigurationSystem/Client/Helpers/Registry.py +38 -26
  8. DIRAC/ConfigurationSystem/Client/Helpers/Resources.py +11 -43
  9. DIRAC/ConfigurationSystem/Client/Helpers/test/Test_Helpers.py +0 -16
  10. DIRAC/ConfigurationSystem/Client/LocalConfiguration.py +14 -8
  11. DIRAC/ConfigurationSystem/Client/PathFinder.py +47 -8
  12. DIRAC/ConfigurationSystem/Client/SyncPlugins/CERNLDAPSyncPlugin.py +4 -1
  13. DIRAC/ConfigurationSystem/Client/VOMS2CSSynchronizer.py +32 -19
  14. DIRAC/ConfigurationSystem/Client/test/Test_PathFinder.py +41 -1
  15. DIRAC/ConfigurationSystem/private/RefresherBase.py +4 -2
  16. DIRAC/Core/Base/API.py +4 -7
  17. DIRAC/Core/Base/SQLAlchemyDB.py +1 -0
  18. DIRAC/Core/DISET/ServiceReactor.py +11 -3
  19. DIRAC/Core/DISET/private/BaseClient.py +1 -2
  20. DIRAC/Core/DISET/private/Transports/M2SSLTransport.py +9 -7
  21. DIRAC/Core/DISET/private/Transports/SSL/M2Utils.py +3 -1
  22. DIRAC/Core/LCG/GOCDBClient.py +5 -7
  23. DIRAC/Core/Security/DiracX.py +31 -17
  24. DIRAC/Core/Security/IAMService.py +5 -10
  25. DIRAC/Core/Security/Locations.py +27 -18
  26. DIRAC/Core/Security/ProxyInfo.py +9 -5
  27. DIRAC/Core/Security/VOMSService.py +2 -4
  28. DIRAC/Core/Security/m2crypto/X509Certificate.py +4 -6
  29. DIRAC/Core/Security/m2crypto/asn1_utils.py +17 -5
  30. DIRAC/Core/Security/test/test_diracx_token_from_pem.py +161 -0
  31. DIRAC/Core/Tornado/Client/ClientSelector.py +4 -1
  32. DIRAC/Core/Tornado/Server/TornadoService.py +1 -1
  33. DIRAC/Core/Utilities/CGroups2.py +328 -0
  34. DIRAC/Core/Utilities/ClassAd/ClassAdLight.py +4 -290
  35. DIRAC/Core/Utilities/DErrno.py +5 -309
  36. DIRAC/Core/Utilities/Extensions.py +10 -1
  37. DIRAC/Core/Utilities/File.py +1 -1
  38. DIRAC/Core/Utilities/Graphs/GraphData.py +1 -1
  39. DIRAC/Core/Utilities/Graphs/GraphUtilities.py +6 -1
  40. DIRAC/Core/Utilities/JDL.py +1 -195
  41. DIRAC/Core/Utilities/List.py +1 -124
  42. DIRAC/Core/Utilities/MySQL.py +103 -99
  43. DIRAC/Core/Utilities/Os.py +32 -1
  44. DIRAC/Core/Utilities/Platform.py +2 -107
  45. DIRAC/Core/Utilities/Proxy.py +0 -4
  46. DIRAC/Core/Utilities/ReturnValues.py +7 -252
  47. DIRAC/Core/Utilities/StateMachine.py +12 -178
  48. DIRAC/Core/Utilities/Subprocess.py +35 -14
  49. DIRAC/Core/Utilities/TimeUtilities.py +10 -253
  50. DIRAC/Core/Utilities/test/Test_JDL.py +0 -3
  51. DIRAC/Core/Utilities/test/Test_Profiler.py +20 -20
  52. DIRAC/Core/scripts/dirac_agent.py +1 -1
  53. DIRAC/Core/scripts/dirac_apptainer_exec.py +72 -46
  54. DIRAC/Core/scripts/dirac_configure.py +1 -3
  55. DIRAC/Core/scripts/dirac_install_db.py +24 -6
  56. DIRAC/Core/scripts/dirac_platform.py +1 -92
  57. DIRAC/DataManagementSystem/Agent/FTS3Agent.py +8 -7
  58. DIRAC/DataManagementSystem/Agent/RequestOperations/RemoveFile.py +7 -6
  59. DIRAC/DataManagementSystem/Client/FTS3Job.py +71 -34
  60. DIRAC/DataManagementSystem/DB/FTS3DB.py +7 -3
  61. DIRAC/DataManagementSystem/DB/FileCatalogComponents/DatasetManager/DatasetManager.py +1 -1
  62. DIRAC/DataManagementSystem/DB/FileCatalogDB.sql +9 -9
  63. DIRAC/DataManagementSystem/DB/FileCatalogWithFkAndPsDB.sql +9 -9
  64. DIRAC/DataManagementSystem/Utilities/DMSHelpers.py +6 -2
  65. DIRAC/DataManagementSystem/scripts/dirac_admin_allow_se.py +13 -8
  66. DIRAC/DataManagementSystem/scripts/dirac_admin_ban_se.py +13 -8
  67. DIRAC/DataManagementSystem/scripts/dirac_dms_create_moving_request.py +2 -0
  68. DIRAC/DataManagementSystem/scripts/dirac_dms_protocol_matrix.py +0 -1
  69. DIRAC/FrameworkSystem/Client/BundleDeliveryClient.py +2 -7
  70. DIRAC/FrameworkSystem/Client/ComponentInstaller.py +9 -4
  71. DIRAC/FrameworkSystem/Client/ProxyManagerClient.py +5 -2
  72. DIRAC/FrameworkSystem/Client/SystemAdministratorClientCLI.py +11 -6
  73. DIRAC/FrameworkSystem/ConfigTemplate.cfg +2 -0
  74. DIRAC/FrameworkSystem/DB/AuthDB.py +3 -3
  75. DIRAC/FrameworkSystem/DB/InstalledComponentsDB.py +4 -4
  76. DIRAC/FrameworkSystem/DB/ProxyDB.py +11 -3
  77. DIRAC/FrameworkSystem/DB/TokenDB.py +1 -1
  78. DIRAC/FrameworkSystem/Service/ProxyManagerHandler.py +8 -6
  79. DIRAC/FrameworkSystem/Utilities/MonitoringUtilities.py +2 -19
  80. DIRAC/FrameworkSystem/Utilities/TokenManagementUtilities.py +3 -2
  81. DIRAC/FrameworkSystem/Utilities/diracx.py +36 -14
  82. DIRAC/FrameworkSystem/private/authorization/AuthServer.py +2 -2
  83. DIRAC/FrameworkSystem/scripts/dirac_admin_update_pilot.py +18 -11
  84. DIRAC/FrameworkSystem/scripts/dirac_login.py +2 -2
  85. DIRAC/FrameworkSystem/scripts/dirac_proxy_init.py +7 -8
  86. DIRAC/Interfaces/API/Dirac.py +27 -15
  87. DIRAC/Interfaces/API/DiracAdmin.py +45 -17
  88. DIRAC/Interfaces/API/Job.py +9 -13
  89. DIRAC/Interfaces/scripts/dirac_admin_allow_site.py +12 -18
  90. DIRAC/Interfaces/scripts/dirac_admin_ban_site.py +12 -10
  91. DIRAC/Interfaces/scripts/dirac_admin_get_site_mask.py +4 -13
  92. DIRAC/Interfaces/scripts/dirac_admin_reset_job.py +3 -6
  93. DIRAC/Interfaces/scripts/dirac_wms_job_parameters.py +0 -1
  94. DIRAC/MonitoringSystem/Client/Types/WMSHistory.py +4 -0
  95. DIRAC/MonitoringSystem/Client/WebAppClient.py +26 -0
  96. DIRAC/MonitoringSystem/ConfigTemplate.cfg +9 -0
  97. DIRAC/MonitoringSystem/DB/MonitoringDB.py +6 -25
  98. DIRAC/MonitoringSystem/Service/MonitoringHandler.py +0 -33
  99. DIRAC/MonitoringSystem/Service/WebAppHandler.py +599 -0
  100. DIRAC/MonitoringSystem/private/MainReporter.py +0 -3
  101. DIRAC/ProductionSystem/DB/ProductionDB.sql +4 -4
  102. DIRAC/ProductionSystem/scripts/dirac_prod_get.py +2 -2
  103. DIRAC/ProductionSystem/scripts/dirac_prod_get_all.py +2 -2
  104. DIRAC/ProductionSystem/scripts/dirac_prod_get_trans.py +2 -3
  105. DIRAC/RequestManagementSystem/Agent/RequestExecutingAgent.py +8 -6
  106. DIRAC/RequestManagementSystem/Agent/RequestOperations/ForwardDISET.py +2 -14
  107. DIRAC/RequestManagementSystem/Client/ReqClient.py +66 -13
  108. DIRAC/RequestManagementSystem/ConfigTemplate.cfg +6 -6
  109. DIRAC/RequestManagementSystem/DB/RequestDB.py +10 -5
  110. DIRAC/RequestManagementSystem/DB/test/RMSTestScenari.py +2 -0
  111. DIRAC/RequestManagementSystem/private/RequestValidator.py +40 -46
  112. DIRAC/ResourceStatusSystem/Client/SiteStatus.py +4 -2
  113. DIRAC/ResourceStatusSystem/Command/FreeDiskSpaceCommand.py +3 -1
  114. DIRAC/ResourceStatusSystem/DB/ResourceManagementDB.py +8 -8
  115. DIRAC/ResourceStatusSystem/DB/ResourceStatusDB.py +2 -2
  116. DIRAC/ResourceStatusSystem/Utilities/CSHelpers.py +2 -31
  117. DIRAC/ResourceStatusSystem/scripts/dirac_rss_set_status.py +30 -12
  118. DIRAC/Resources/Catalog/RucioFileCatalogClient.py +195 -1
  119. DIRAC/Resources/Catalog/test/Test_RucioFileCatalogClient.py +181 -0
  120. DIRAC/Resources/Computing/AREXComputingElement.py +25 -8
  121. DIRAC/Resources/Computing/BatchSystems/Condor.py +126 -108
  122. DIRAC/Resources/Computing/BatchSystems/SLURM.py +5 -1
  123. DIRAC/Resources/Computing/BatchSystems/test/Test_SLURM.py +46 -0
  124. DIRAC/Resources/Computing/ComputingElement.py +1 -1
  125. DIRAC/Resources/Computing/HTCondorCEComputingElement.py +44 -44
  126. DIRAC/Resources/Computing/InProcessComputingElement.py +4 -2
  127. DIRAC/Resources/Computing/LocalComputingElement.py +1 -18
  128. DIRAC/Resources/Computing/SSHBatchComputingElement.py +1 -17
  129. DIRAC/Resources/Computing/SSHComputingElement.py +1 -18
  130. DIRAC/Resources/Computing/SingularityComputingElement.py +19 -5
  131. DIRAC/Resources/Computing/test/Test_HTCondorCEComputingElement.py +67 -49
  132. DIRAC/Resources/Computing/test/Test_PoolComputingElement.py +2 -1
  133. DIRAC/Resources/IdProvider/CheckInIdProvider.py +13 -0
  134. DIRAC/Resources/IdProvider/IdProviderFactory.py +11 -3
  135. DIRAC/Resources/MessageQueue/StompMQConnector.py +1 -1
  136. DIRAC/Resources/Storage/GFAL2_StorageBase.py +24 -15
  137. DIRAC/Resources/Storage/OccupancyPlugins/WLCGAccountingHTTPJson.py +1 -3
  138. DIRAC/Resources/Storage/StorageBase.py +4 -2
  139. DIRAC/Resources/Storage/StorageElement.py +6 -7
  140. DIRAC/StorageManagementSystem/DB/StorageManagementDB.sql +2 -2
  141. DIRAC/TransformationSystem/Agent/TaskManagerAgentBase.py +10 -16
  142. DIRAC/TransformationSystem/Agent/TransformationAgent.py +22 -1
  143. DIRAC/TransformationSystem/Agent/TransformationCleaningAgent.py +16 -16
  144. DIRAC/TransformationSystem/Client/TaskManager.py +2 -4
  145. DIRAC/TransformationSystem/Client/Transformation.py +6 -7
  146. DIRAC/TransformationSystem/Client/TransformationClient.py +21 -11
  147. DIRAC/TransformationSystem/Client/Utilities.py +9 -0
  148. DIRAC/TransformationSystem/DB/TransformationDB.py +11 -14
  149. DIRAC/TransformationSystem/DB/TransformationDB.sql +9 -9
  150. DIRAC/TransformationSystem/Service/TransformationManagerHandler.py +0 -333
  151. DIRAC/TransformationSystem/Utilities/ReplicationCLIParameters.py +3 -3
  152. DIRAC/TransformationSystem/Utilities/TransformationInfo.py +7 -5
  153. DIRAC/TransformationSystem/scripts/dirac_production_runjoblocal.py +2 -4
  154. DIRAC/TransformationSystem/test/Test_TransformationInfo.py +22 -15
  155. DIRAC/TransformationSystem/test/Test_replicationTransformation.py +5 -6
  156. DIRAC/Workflow/Modules/test/Test_Modules.py +5 -0
  157. DIRAC/WorkloadManagementSystem/Agent/JobAgent.py +38 -26
  158. DIRAC/WorkloadManagementSystem/Agent/JobCleaningAgent.py +12 -8
  159. DIRAC/WorkloadManagementSystem/Agent/PilotSyncAgent.py +4 -3
  160. DIRAC/WorkloadManagementSystem/Agent/PushJobAgent.py +13 -13
  161. DIRAC/WorkloadManagementSystem/Agent/SiteDirector.py +18 -14
  162. DIRAC/WorkloadManagementSystem/Agent/StalledJobAgent.py +18 -51
  163. DIRAC/WorkloadManagementSystem/Agent/StatesAccountingAgent.py +41 -1
  164. DIRAC/WorkloadManagementSystem/Agent/test/Test_Agent_JobAgent.py +45 -4
  165. DIRAC/WorkloadManagementSystem/Agent/test/Test_Agent_JobCleaningAgent.py +7 -9
  166. DIRAC/WorkloadManagementSystem/Agent/test/Test_Agent_PushJobAgent.py +1 -0
  167. DIRAC/WorkloadManagementSystem/Agent/test/Test_Agent_SiteDirector.py +9 -2
  168. DIRAC/WorkloadManagementSystem/Agent/test/Test_Agent_StalledJobAgent.py +4 -5
  169. DIRAC/WorkloadManagementSystem/Client/DownloadInputData.py +9 -9
  170. DIRAC/WorkloadManagementSystem/Client/InputDataResolution.py +6 -6
  171. DIRAC/WorkloadManagementSystem/Client/JobMonitoringClient.py +10 -11
  172. DIRAC/WorkloadManagementSystem/Client/JobReport.py +1 -1
  173. DIRAC/WorkloadManagementSystem/Client/JobState/CachedJobState.py +3 -0
  174. DIRAC/WorkloadManagementSystem/Client/JobState/JobManifest.py +32 -261
  175. DIRAC/WorkloadManagementSystem/Client/JobState/JobState.py +6 -0
  176. DIRAC/WorkloadManagementSystem/Client/JobStateUpdateClient.py +3 -0
  177. DIRAC/WorkloadManagementSystem/Client/JobStatus.py +8 -152
  178. DIRAC/WorkloadManagementSystem/Client/PoolXMLSlice.py +12 -19
  179. DIRAC/WorkloadManagementSystem/Client/SandboxStoreClient.py +25 -38
  180. DIRAC/WorkloadManagementSystem/Client/WMSClient.py +2 -3
  181. DIRAC/WorkloadManagementSystem/Client/test/Test_Client_DownloadInputData.py +29 -0
  182. DIRAC/WorkloadManagementSystem/ConfigTemplate.cfg +4 -8
  183. DIRAC/WorkloadManagementSystem/DB/JobDB.py +89 -132
  184. DIRAC/WorkloadManagementSystem/DB/JobDB.sql +8 -8
  185. DIRAC/WorkloadManagementSystem/DB/JobDBUtils.py +18 -147
  186. DIRAC/WorkloadManagementSystem/DB/JobLoggingDB.py +19 -6
  187. DIRAC/WorkloadManagementSystem/DB/JobParametersDB.py +9 -9
  188. DIRAC/WorkloadManagementSystem/DB/PilotAgentsDB.py +16 -5
  189. DIRAC/WorkloadManagementSystem/DB/PilotAgentsDB.sql +3 -3
  190. DIRAC/WorkloadManagementSystem/DB/SandboxMetadataDB.py +44 -82
  191. DIRAC/WorkloadManagementSystem/DB/StatusUtils.py +125 -0
  192. DIRAC/WorkloadManagementSystem/DB/tests/Test_JobDB.py +1 -1
  193. DIRAC/WorkloadManagementSystem/DB/tests/Test_StatusUtils.py +28 -0
  194. DIRAC/WorkloadManagementSystem/Executor/JobSanity.py +5 -4
  195. DIRAC/WorkloadManagementSystem/Executor/JobScheduling.py +4 -0
  196. DIRAC/WorkloadManagementSystem/FutureClient/JobStateUpdateClient.py +75 -33
  197. DIRAC/WorkloadManagementSystem/JobWrapper/JobWrapper.py +22 -11
  198. DIRAC/WorkloadManagementSystem/JobWrapper/JobWrapperTemplate.py +9 -10
  199. DIRAC/WorkloadManagementSystem/JobWrapper/test/Test_JobWrapper.py +60 -10
  200. DIRAC/WorkloadManagementSystem/JobWrapper/test/Test_JobWrapperTemplate.py +4 -0
  201. DIRAC/WorkloadManagementSystem/Service/JobManagerHandler.py +33 -154
  202. DIRAC/WorkloadManagementSystem/Service/JobMonitoringHandler.py +5 -323
  203. DIRAC/WorkloadManagementSystem/Service/JobStateUpdateHandler.py +0 -16
  204. DIRAC/WorkloadManagementSystem/Service/PilotManagerHandler.py +6 -103
  205. DIRAC/WorkloadManagementSystem/Service/SandboxStoreHandler.py +7 -53
  206. DIRAC/WorkloadManagementSystem/Service/WMSAdministratorHandler.py +16 -79
  207. DIRAC/WorkloadManagementSystem/Service/WMSUtilities.py +4 -18
  208. DIRAC/WorkloadManagementSystem/Utilities/JobModel.py +28 -209
  209. DIRAC/WorkloadManagementSystem/Utilities/JobParameters.py +65 -3
  210. DIRAC/WorkloadManagementSystem/Utilities/JobStatusUtility.py +2 -64
  211. DIRAC/WorkloadManagementSystem/Utilities/ParametricJob.py +7 -171
  212. DIRAC/WorkloadManagementSystem/Utilities/PilotCStoJSONSynchronizer.py +73 -7
  213. DIRAC/WorkloadManagementSystem/Utilities/PilotWrapper.py +41 -11
  214. DIRAC/WorkloadManagementSystem/Utilities/RemoteRunner.py +16 -0
  215. DIRAC/WorkloadManagementSystem/Utilities/Utils.py +36 -1
  216. DIRAC/WorkloadManagementSystem/Utilities/jobAdministration.py +15 -0
  217. DIRAC/WorkloadManagementSystem/Utilities/test/Test_JobModel.py +1 -15
  218. DIRAC/WorkloadManagementSystem/Utilities/test/Test_ParametricJob.py +45 -128
  219. DIRAC/WorkloadManagementSystem/Utilities/test/Test_PilotWrapper.py +16 -0
  220. DIRAC/WorkloadManagementSystem/scripts/dirac_jobexec.py +7 -2
  221. DIRAC/WorkloadManagementSystem/scripts/dirac_wms_pilot_job_info.py +1 -1
  222. DIRAC/__init__.py +62 -60
  223. DIRAC/tests/Utilities/testJobDefinitions.py +22 -28
  224. {DIRAC-9.0.0a42.dist-info → dirac-9.0.7.dist-info}/METADATA +8 -5
  225. {DIRAC-9.0.0a42.dist-info → dirac-9.0.7.dist-info}/RECORD +229 -228
  226. {DIRAC-9.0.0a42.dist-info → dirac-9.0.7.dist-info}/WHEEL +1 -1
  227. {DIRAC-9.0.0a42.dist-info → dirac-9.0.7.dist-info}/entry_points.txt +0 -3
  228. DIRAC/Core/Utilities/test/Test_List.py +0 -150
  229. DIRAC/Core/Utilities/test/Test_Time.py +0 -88
  230. DIRAC/Resources/Computing/PilotBundle.py +0 -70
  231. DIRAC/TransformationSystem/scripts/dirac_transformation_archive.py +0 -30
  232. DIRAC/TransformationSystem/scripts/dirac_transformation_clean.py +0 -30
  233. DIRAC/TransformationSystem/scripts/dirac_transformation_remove_output.py +0 -30
  234. DIRAC/WorkloadManagementSystem/Utilities/test/Test_JobManager.py +0 -58
  235. {DIRAC-9.0.0a42.dist-info → dirac-9.0.7.dist-info/licenses}/LICENSE +0 -0
  236. {DIRAC-9.0.0a42.dist-info → dirac-9.0.7.dist-info}/top_level.txt +0 -0
@@ -1,124 +1 @@
1
- """Collection of DIRAC useful list related modules.
2
- By default on Error they return None.
3
- """
4
- import random
5
- import sys
6
- from typing import Any
7
-
8
-
9
- def uniqueElements(aList: list) -> list:
10
- """Utility to retrieve list of unique elements in a list (order is kept)."""
11
-
12
- # Use dict.fromkeys instead of set ensure the order is preserved
13
- return list(dict.fromkeys(aList))
14
-
15
-
16
- def appendUnique(aList: list, anObject: Any):
17
- """Append to list if object does not exist.
18
-
19
- :param aList: list of elements
20
- :param anObject: object you want to append
21
- """
22
- if anObject not in aList:
23
- aList.append(anObject)
24
-
25
-
26
- def fromChar(inputString: str, sepChar: str = ","):
27
- """Generates a list splitting a string by the required character(s)
28
- resulting string items are stripped and empty items are removed.
29
-
30
- :param inputString: list serialised to string
31
- :param sepChar: separator
32
- :return: list of strings or None if sepChar has a wrong type
33
- """
34
- # to prevent getting an empty String as argument
35
- if not (isinstance(inputString, str) and isinstance(sepChar, str) and sepChar):
36
- return None
37
- return [fieldString.strip() for fieldString in inputString.split(sepChar) if len(fieldString.strip()) > 0]
38
-
39
-
40
- def randomize(aList: list) -> list:
41
- """Return a randomly sorted list.
42
-
43
- :param aList: list to permute
44
- """
45
- tmpList = list(aList)
46
- random.shuffle(tmpList)
47
- return tmpList
48
-
49
-
50
- def pop(aList, popElement):
51
- """Pop the first element equal to popElement from the list.
52
-
53
- :param aList: list
54
- :type aList: python:list
55
- :param popElement: element to pop
56
- """
57
- if popElement in aList:
58
- return aList.pop(aList.index(popElement))
59
-
60
-
61
- def stringListToString(aList: list) -> str:
62
- """This function is used for making MySQL queries with a list of string elements.
63
-
64
- :param aList: list to be serialized to string for making queries
65
- """
66
- return ",".join(f"'{x}'" for x in aList)
67
-
68
-
69
- def intListToString(aList: list) -> str:
70
- """This function is used for making MySQL queries with a list of int elements.
71
-
72
- :param aList: list to be serialized to string for making queries
73
- """
74
- return ",".join(str(x) for x in aList)
75
-
76
-
77
- def getChunk(aList: list, chunkSize: int):
78
- """Generator yielding chunk from a list of a size chunkSize.
79
-
80
- :param aList: list to be splitted
81
- :param chunkSize: lenght of one chunk
82
- :raise: StopIteration
83
-
84
- Usage:
85
-
86
- >>> for chunk in getChunk( aList, chunkSize=10):
87
- process( chunk )
88
-
89
- """
90
- chunkSize = int(chunkSize)
91
- for i in range(0, len(aList), chunkSize):
92
- yield aList[i : i + chunkSize]
93
-
94
-
95
- def breakListIntoChunks(aList: list, chunkSize: int):
96
- """This function takes a list as input and breaks it into list of size 'chunkSize'.
97
- It returns a list of lists.
98
-
99
- :param aList: list of elements
100
- :param chunkSize: len of a single chunk
101
- :return: list of lists of length of chunkSize
102
- :raise: RuntimeError if numberOfFilesInChunk is less than 1
103
- """
104
- if chunkSize < 1:
105
- raise RuntimeError("chunkSize cannot be less than 1")
106
- if isinstance(aList, (set, dict, tuple, {}.keys().__class__, {}.items().__class__, {}.values().__class__)):
107
- aList = list(aList)
108
- return [chunk for chunk in getChunk(aList, chunkSize)]
109
-
110
-
111
- def getIndexInList(anItem: Any, aList: list) -> int:
112
- """Return the index of the element x in the list l
113
- or sys.maxint if it does not exist
114
-
115
- :param anItem: element to look for
116
- :param aList: list to look into
117
-
118
- :return: the index or sys.maxint
119
- """
120
- # try:
121
- if anItem in aList:
122
- return aList.index(anItem)
123
- else:
124
- return sys.maxsize
1
+ from DIRACCommon.Core.Utilities.List import * # noqa: F401,F403
@@ -1,151 +1,152 @@
1
- """ DIRAC Basic MySQL Class
2
- It provides access to the basic MySQL methods in a multithread-safe mode
3
- keeping used connections in a python Queue for further reuse.
1
+ """DIRAC Basic MySQL Class
2
+ It provides access to the basic MySQL methods in a multithread-safe mode
3
+ keeping used connections in a python Queue for further reuse.
4
4
 
5
- These are the coded methods:
5
+ These are the coded methods:
6
6
 
7
7
 
8
- __init__( host, user, passwd, name, [maxConnsInQueue=10] )
8
+ __init__( host, user, passwd, name, [maxConnsInQueue=10] )
9
9
 
10
- Initializes the Queue and tries to connect to the DB server,
11
- using the _connect method.
12
- "maxConnsInQueue" defines the size of the Queue of open connections
13
- that are kept for reuse. It also defined the maximum number of open
14
- connections available from the object.
15
- maxConnsInQueue = 0 means unlimited and it is not supported.
10
+ Initializes the Queue and tries to connect to the DB server,
11
+ using the _connect method.
12
+ "maxConnsInQueue" defines the size of the Queue of open connections
13
+ that are kept for reuse. It also defined the maximum number of open
14
+ connections available from the object.
15
+ maxConnsInQueue = 0 means unlimited and it is not supported.
16
16
 
17
17
 
18
- _except( methodName, exception, errorMessage )
18
+ _except( methodName, exception, errorMessage )
19
19
 
20
- Helper method for exceptions: the "methodName" and the "errorMessage"
21
- are printed with ERROR level, then the "exception" is printed (with
22
- full description if it is a MySQL Exception) and S_ERROR is returned
23
- with the errorMessage and the exception.
20
+ Helper method for exceptions: the "methodName" and the "errorMessage"
21
+ are printed with ERROR level, then the "exception" is printed (with
22
+ full description if it is a MySQL Exception) and S_ERROR is returned
23
+ with the errorMessage and the exception.
24
24
 
25
25
 
26
- _connect()
26
+ _connect()
27
27
 
28
- Attempts connection to DB and sets the _connected flag to True upon success.
29
- Returns S_OK or S_ERROR.
28
+ Attempts connection to DB and sets the _connected flag to True upon success.
29
+ Returns S_OK or S_ERROR.
30
30
 
31
31
 
32
- _query( cmd, [conn=conn] )
32
+ _query( cmd, [conn=conn] )
33
33
 
34
- Executes SQL command "cmd".
35
- Gets a connection from the Queue (or open a new one if none is available),
36
- the used connection is back into the Queue.
37
- If a connection to the the DB is passed as second argument this connection
38
- is used and is not in the Queue.
39
- Returns S_OK with fetchall() out in Value or S_ERROR upon failure.
34
+ Executes SQL command "cmd".
35
+ Gets a connection from the Queue (or open a new one if none is available),
36
+ the used connection is back into the Queue.
37
+ If a connection to the the DB is passed as second argument this connection
38
+ is used and is not in the Queue.
39
+ Returns S_OK with fetchall() out in Value or S_ERROR upon failure.
40
40
 
41
41
 
42
- _update( cmd, [conn=conn] )
42
+ _update( cmd, [conn=conn] )
43
43
 
44
- Executes SQL command "cmd" and issue a commit
45
- Gets a connection from the Queue (or open a new one if none is available),
46
- the used connection is back into the Queue.
47
- If a connection to the the DB is passed as second argument this connection
48
- is used and is not in the Queue
49
- Returns S_OK with number of updated registers in Value or S_ERROR upon failure.
44
+ Executes SQL command "cmd" and issue a commit
45
+ Gets a connection from the Queue (or open a new one if none is available),
46
+ the used connection is back into the Queue.
47
+ If a connection to the the DB is passed as second argument this connection
48
+ is used and is not in the Queue
49
+ Returns S_OK with number of updated registers in Value or S_ERROR upon failure.
50
50
 
51
51
 
52
- _createTables( tableDict )
52
+ _createTables( tableDict )
53
53
 
54
- Create a new Table in the DB
54
+ Create a new Table in the DB
55
55
 
56
56
 
57
- _getConnection()
57
+ _getConnection()
58
58
 
59
- Gets a connection from the Queue (or open a new one if none is available)
60
- Returns S_OK with connection in Value or S_ERROR
61
- the calling method is responsible for closing this connection once it is no
62
- longer needed.
59
+ Gets a connection from the Queue (or open a new one if none is available)
60
+ Returns S_OK with connection in Value or S_ERROR
61
+ the calling method is responsible for closing this connection once it is no
62
+ longer needed.
63
63
 
64
64
 
65
65
 
66
66
 
67
- Some high level methods have been added to avoid the need to write SQL
68
- statement in most common cases. They should be used instead of low level
69
- _insert, _update methods when ever possible.
67
+ Some high level methods have been added to avoid the need to write SQL
68
+ statement in most common cases. They should be used instead of low level
69
+ _insert, _update methods when ever possible.
70
70
 
71
- buildCondition( self, condDict = None, older = None, newer = None,
72
- timeStamp = None, orderAttribute = None, limit = False,
73
- greater = None, smaller = None ):
71
+ buildCondition( self, condDict = None, older = None, newer = None,
72
+ timeStamp = None, orderAttribute = None, limit = False,
73
+ greater = None, smaller = None ):
74
74
 
75
- Build SQL condition statement from provided condDict and other extra check on
76
- a specified time stamp.
77
- The conditions dictionary specifies for each attribute one or a List of possible
78
- values
79
- greater and smaller are dictionaries in which the keys are the names of the fields,
80
- that are requested to be >= or < than the corresponding value.
81
- For compatibility with current usage it uses Exceptions to exit in case of
82
- invalid arguments
75
+ Build SQL condition statement from provided condDict and other extra check on
76
+ a specified time stamp.
77
+ The conditions dictionary specifies for each attribute one or a List of possible
78
+ values
79
+ greater and smaller are dictionaries in which the keys are the names of the fields,
80
+ that are requested to be >= or < than the corresponding value.
81
+ For compatibility with current usage it uses Exceptions to exit in case of
82
+ invalid arguments
83
83
 
84
84
 
85
- insertFields( self, tableName, inFields = None, inValues = None, conn = None, inDict = None ):
85
+ insertFields( self, tableName, inFields = None, inValues = None, conn = None, inDict = None ):
86
86
 
87
- Insert a new row in "tableName" assigning the values "inValues" to the
88
- fields "inFields".
89
- Alternatively inDict can be used
90
- String type values will be appropriately escaped.
87
+ Insert a new row in "tableName" assigning the values "inValues" to the
88
+ fields "inFields".
89
+ Alternatively inDict can be used
90
+ String type values will be appropriately escaped.
91
91
 
92
92
 
93
- updateFields( self, tableName, updateFields = None, updateValues = None,
94
- condDict = None,
95
- limit = False, conn = None,
96
- updateDict = None,
97
- older = None, newer = None,
98
- timeStamp = None, orderAttribute = None ):
93
+ updateFields( self, tableName, updateFields = None, updateValues = None,
94
+ condDict = None,
95
+ limit = False, conn = None,
96
+ updateDict = None,
97
+ older = None, newer = None,
98
+ timeStamp = None, orderAttribute = None ):
99
99
 
100
- Update "updateFields" from "tableName" with "updateValues".
101
- updateDict alternative way to provide the updateFields and updateValues
102
- N records can match the condition
103
- return S_OK( number of updated rows )
104
- if limit is not False, the given limit is set
105
- String type values will be appropriately escaped.
100
+ Update "updateFields" from "tableName" with "updateValues".
101
+ updateDict alternative way to provide the updateFields and updateValues
102
+ N records can match the condition
103
+ return S_OK( number of updated rows )
104
+ if limit is not False, the given limit is set
105
+ String type values will be appropriately escaped.
106
106
 
107
107
 
108
- deleteEntries( self, tableName,
109
- condDict = None,
110
- limit = False, conn = None,
111
- older = None, newer = None,
112
- timeStamp = None, orderAttribute = None ):
113
-
114
- Delete rows from "tableName" with
115
- N records can match the condition
116
- if limit is not False, the given limit is set
117
- String type values will be appropriately escaped, they can be single values or lists of values.
118
-
119
-
120
- getFields( self, tableName, outFields = None,
108
+ deleteEntries( self, tableName,
121
109
  condDict = None,
122
110
  limit = False, conn = None,
123
111
  older = None, newer = None,
124
112
  timeStamp = None, orderAttribute = None ):
125
113
 
126
- Select "outFields" from "tableName" with condDict
127
- N records can match the condition
128
- return S_OK( tuple(Field,Value) )
129
- if limit is not False, the given limit is set
130
- String type values will be appropriately escaped, they can be single values or lists of values.
114
+ Delete rows from "tableName" with
115
+ N records can match the condition
116
+ if limit is not False, the given limit is set
117
+ String type values will be appropriately escaped, they can be single values or lists of values.
118
+
119
+
120
+ getFields( self, tableName, outFields = None,
121
+ condDict = None,
122
+ limit = False, conn = None,
123
+ older = None, newer = None,
124
+ timeStamp = None, orderAttribute = None ):
131
125
 
132
- for compatibility with other methods condDict keyed argument is added
126
+ Select "outFields" from "tableName" with condDict
127
+ N records can match the condition
128
+ return S_OK( tuple(Field,Value) )
129
+ if limit is not False, the given limit is set
130
+ String type values will be appropriately escaped, they can be single values or lists of values.
133
131
 
132
+ for compatibility with other methods condDict keyed argument is added
134
133
 
135
- getCounters( self, table, attrList, condDict = None, older = None,
136
- newer = None, timeStamp = None, connection = False ):
137
134
 
138
- Count the number of records on each distinct combination of AttrList, selected
139
- with condition defined by condDict and time stamps
135
+ getCounters( self, table, attrList, condDict = None, older = None,
136
+ newer = None, timeStamp = None, connection = False ):
140
137
 
138
+ Count the number of records on each distinct combination of AttrList, selected
139
+ with condition defined by condDict and time stamps
141
140
 
142
- getDistinctAttributeValues( self, table, attribute, condDict = None, older = None,
143
- newer = None, timeStamp = None, connection = False ):
144
141
 
145
- Get distinct values of a table attribute under specified conditions
142
+ getDistinctAttributeValues( self, table, attribute, condDict = None, older = None,
143
+ newer = None, timeStamp = None, connection = False ):
144
+
145
+ Get distinct values of a table attribute under specified conditions
146
146
 
147
147
 
148
148
  """
149
+
149
150
  import collections
150
151
  import functools
151
152
  import json
@@ -760,6 +761,7 @@ class MySQL:
760
761
 
761
762
  :return: S_OK with number of updated registers upon success.
762
763
  S_ERROR upon error.
764
+ lastRowId: if set, added to the returned dictionary
763
765
  """
764
766
 
765
767
  self.log.debug(f"_update: {self._safeCmd(cmd)}")
@@ -774,9 +776,11 @@ class MySQL:
774
776
  try:
775
777
  cursor = connection.cursor()
776
778
  res = cursor.execute(cmd, args=args)
779
+
777
780
  retDict = S_OK(res)
778
781
  if cursor.lastrowid:
779
782
  retDict["lastRowId"] = cursor.lastrowid
783
+
780
784
  except Exception as x:
781
785
  retDict = self._except("_update", x, "Execution failed.", cmd, debug)
782
786
 
@@ -929,7 +933,7 @@ class MySQL:
929
933
  index is the list of fields to be indexed. This indexes will declared
930
934
  unique.
931
935
  "Engine": use the given DB engine, InnoDB is the default if not present.
932
- "Charset": use the given character set. Default is latin1
936
+ "Charset": use the given character set. Default is utf8mb4
933
937
  force:
934
938
  if True, requested tables are DROP if they exist.
935
939
  if False, returned with S_ERROR if table exist.
@@ -1046,7 +1050,7 @@ class MySQL:
1046
1050
  )
1047
1051
 
1048
1052
  engine = thisTable.get("Engine", "InnoDB")
1049
- charset = thisTable.get("Charset", "latin1")
1053
+ charset = thisTable.get("Charset", "utf8mb4")
1050
1054
 
1051
1055
  cmd = "CREATE TABLE `{}` (\n{}\n) ENGINE={} DEFAULT CHARSET={}".format(
1052
1056
  table,
@@ -3,10 +3,11 @@
3
3
  by default on Error they return None
4
4
  """
5
5
  import os
6
+ import threading
6
7
 
7
8
  import DIRAC
8
- from DIRAC.Core.Utilities.Subprocess import shellCall, systemCall
9
9
  from DIRAC.Core.Utilities import List
10
+ from DIRAC.Core.Utilities.Subprocess import shellCall, systemCall
10
11
 
11
12
  DEBUG = 0
12
13
 
@@ -128,3 +129,33 @@ def sourceEnv(timeout, cmdTuple, inputEnv=None):
128
129
  result["stderr"] = stderr
129
130
 
130
131
  return result
132
+
133
+
134
+ def safe_listdir(directory, timeout=60):
135
+ """This is a "safe" list directory,
136
+ for lazily-loaded File Systems like CVMFS.
137
+ There's by default a 60 seconds timeout.
138
+
139
+ .. warning::
140
+ There is no distinction between an empty directory, and a non existent one.
141
+ It will return `[]` in both cases.
142
+
143
+ :param str directory: directory to list
144
+ :param int timeout: optional timeout, in seconds. Defaults to 60.
145
+ """
146
+
147
+ def listdir(directory):
148
+ try:
149
+ return os.listdir(directory)
150
+ except FileNotFoundError:
151
+ print(f"{directory} not found")
152
+ return []
153
+
154
+ contents = []
155
+ t = threading.Thread(target=lambda: contents.extend(listdir(directory)))
156
+ t.daemon = True # don't delay program's exit
157
+ t.start()
158
+ t.join(timeout)
159
+ if t.is_alive():
160
+ return None # timeout
161
+ return contents
@@ -2,119 +2,14 @@
2
2
  Compile the externals
3
3
  """
4
4
  import platform
5
- import sys
6
- import os
7
- import re
8
-
9
- # We need to patch python platform module. It does a string comparison for the libc versions.
10
- # it fails when going from 2.9 to 2.10,
11
- # the fix converts the version to a tuple and attempts a numeric comparison
12
-
13
- _libc_search = re.compile(b"(__libc_init)" b"|" b"(GLIBC_([0-9.]+))" b"|" b"(libc(_\\w+)?\\.so(?:\\.(\\d[0-9.]*))?)")
14
-
15
-
16
- def libc_ver(executable=sys.executable, lib="", version="", chunksize=2048):
17
- """Tries to determine the libc version that the file executable
18
- (which defaults to the Python interpreter) is linked against.
19
-
20
- Returns a tuple of strings (lib,version) which default to the
21
- given parameters in case the lookup fails.
22
-
23
- Note that the function has intimate knowledge of how different
24
- libc versions add symbols to the executable and thus is probably
25
- only useable for executables compiled using gcc.
26
-
27
- The file is read and scanned in chunks of chunksize bytes.
28
-
29
- """
30
- with open(executable, "rb") as f:
31
- binary = f.read(chunksize)
32
- pos = 0
33
- version = [0, 0, 0]
34
- while True:
35
- m = _libc_search.search(binary, pos)
36
- if not m:
37
- binary = f.read(chunksize)
38
- if not binary:
39
- break
40
- pos = 0
41
- continue
42
- libcinit, glibc, glibcversion, so, threads, soversion = m.groups()
43
- if libcinit and not lib:
44
- lib = b"libc"
45
- elif glibc:
46
- glibcversion_parts = glibcversion.split(b".")
47
- for i, part in enumerate(glibcversion_parts):
48
- try:
49
- glibcversion_parts[i] = int(part)
50
- except ValueError:
51
- glibcversion_parts[i] = 0
52
- if libcinit and not lib:
53
- lib = b"libc"
54
- elif glibc:
55
- if lib != b"glibc":
56
- lib = b"glibc"
57
- version = glibcversion_parts
58
- elif glibcversion_parts > version:
59
- version = glibcversion_parts
60
- elif so:
61
- if lib != b"glibc":
62
- lib = b"libc"
63
- version = max(version, [int(soversion)]).pop()
64
- if threads and version[-len(threads) :] != threads:
65
- version = version + threads
66
- pos = m.end()
67
- return lib.decode(), ".".join(map(str, version))
68
-
69
-
70
- # ## Command line interface
71
5
 
72
6
 
7
+ # Command line interface
73
8
  def getPlatformString():
74
9
  # Modified to return our desired platform string, R. Graciani
75
10
  platformTuple = (platform.system(), platform.machine())
76
11
  if platformTuple[0] == "Linux":
77
- try:
78
- import subprocess
79
-
80
- sp = subprocess.Popen(["/sbin/ldconfig", "--print-cache"], stdout=subprocess.PIPE, universal_newlines=True)
81
- spStdout = sp.stdout
82
- except Exception:
83
- sp = None
84
- spStdout = os.popen("/sbin/ldconfig --print-cache", "r")
85
- ldre = re.compile(r".*=> (.*/libc\.so\..*$)")
86
- libs = []
87
- for line in spStdout.readlines():
88
- reM = ldre.match(line)
89
- if reM:
90
- libs.append(reM.groups()[0])
91
- if sp:
92
- if "terminate" in dir(sp):
93
- sp.terminate()
94
- sp.wait()
95
-
96
- if not libs:
97
- # get version of higher libc installed
98
- if platform.machine().find("64") != -1:
99
- lib = "/lib64"
100
- else:
101
- lib = "/lib"
102
- for libFile in os.listdir(lib):
103
- if libFile.find("libc-") == 0 or libFile.find("libc.so") == 0:
104
- libs.append(os.path.join(lib, libFile))
105
- newest_lib = [0, 0, 0]
106
- for lib in libs:
107
- lib_parts = libc_ver(lib)[1].split(".")
108
- for i, part in enumerate(lib_parts):
109
- try:
110
- lib_parts[i] = int(part)
111
- except ValueError:
112
- lib_parts[i] = 0
113
- # print "non integer version numbers"
114
- if lib_parts > newest_lib:
115
- newest_lib = lib_parts
116
-
117
- platformTuple += ("glibc-" + ".".join(map(str, newest_lib)),)
12
+ platformTuple += ("-".join(platform.libc_ver()),)
118
13
  elif platformTuple[0] == "Darwin":
119
14
  platformTuple += (".".join(platform.mac_ver()[0].split(".")[:2]),)
120
15
  else:
@@ -160,10 +160,6 @@ def executeWithoutServerCertificate(fcn):
160
160
 
161
161
  try:
162
162
  return fcn(*args, **kwargs)
163
- except Exception as lException: # pylint: disable=broad-except
164
- value = ",".join([str(arg) for arg in lException.args])
165
- exceptType = lException.__class__.__name__
166
- return S_ERROR(f"Exception - {exceptType}: {value}")
167
163
  finally:
168
164
  # Restore the default host certificate usage if necessary
169
165
  if useServerCertificate: