Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commite1e609e

Browse files
PostgresNodePortManager__Generic is added
1 parent0f842fd commite1e609e

File tree

5 files changed

+106
-69
lines changed

5 files changed

+106
-69
lines changed

‎testgres/node.py

Lines changed: 53 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -100,6 +100,8 @@
100100
options_string, \
101101
clean_on_error
102102

103+
from .helpers.port_managerimportPortForException
104+
103105
from .backupimportNodeBackup
104106

105107
from .operations.os_opsimportConnectionParams
@@ -172,6 +174,52 @@ def release_port(self, number: int) -> None:
172174
returnutils.release_port(number)
173175

174176

177+
classPostgresNodePortManager__Generic(PostgresNodePortManager):
178+
_os_ops:OsOperations
179+
_allocated_ports_guard:object
180+
_allocated_ports:set[int]
181+
182+
def__init__(self,os_ops:OsOperations):
183+
assertos_opsisnotNone
184+
assertisinstance(os_ops,OsOperations)
185+
self._os_ops=os_ops
186+
self._allocated_ports_guard=threading.Lock()
187+
self._allocated_ports=set[int]()
188+
189+
defreserve_port(self)->int:
190+
ports=set(range(1024,65535))
191+
asserttype(ports)==set# noqa: E721
192+
193+
assertself._allocated_ports_guardisnotNone
194+
asserttype(self._allocated_ports)==set# noqa: E721
195+
196+
withself._allocated_ports_guard:
197+
ports.difference_update(self._allocated_ports)
198+
199+
sampled_ports=random.sample(tuple(ports),min(len(ports),100))
200+
201+
forportinsampled_ports:
202+
assertnot (portinself._allocated_ports)
203+
204+
ifnotself._os_ops.is_port_free(port):
205+
continue
206+
207+
self._allocated_ports.add(port)
208+
returnport
209+
210+
raisePortForException("Can't select a port")
211+
212+
defrelease_port(self,number:int)->None:
213+
asserttype(number)==int# noqa: E721
214+
215+
assertself._allocated_ports_guardisnotNone
216+
asserttype(self._allocated_ports)==set# noqa: E721
217+
218+
withself._allocated_ports_guard:
219+
assertnumberinself._allocated_ports
220+
self._allocated_ports.discard(number)
221+
222+
175223
classPostgresNode(object):
176224
# a max number of node start attempts
177225
_C_MAX_START_ATEMPTS=5
@@ -308,8 +356,11 @@ def _get_port_manager(os_ops: OsOperations) -> PostgresNodePortManager:
308356
assertos_opsisnotNone
309357
assertisinstance(os_ops,OsOperations)
310358

311-
# [2025-04-03] It is our old, incorrected behaviour
312-
returnPostgresNodePortManager__ThisHost()
359+
ifisinstance(os_ops,LocalOperations):
360+
returnPostgresNodePortManager__ThisHost()
361+
362+
# TODO: Throw exception "Please define a port manager."
363+
returnPostgresNodePortManager__Generic(os_ops)
313364

314365
defclone_with_new_name_and_base_dir(self,name:str,base_dir:str):
315366
assertnameisNoneortype(name)==str# noqa: E721

‎testgres/operations/local_ops.py

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
importsubprocess
77
importtempfile
88
importtime
9+
importsocket
910

1011
importpsutil
1112

@@ -436,6 +437,16 @@ def get_process_children(self, pid):
436437
asserttype(pid)==int# noqa: E721
437438
returnpsutil.Process(pid).children()
438439

440+
defis_port_free(self,number:int)->bool:
441+
asserttype(number)==int# noqa: E721
442+
443+
withsocket.socket(socket.AF_INET,socket.SOCK_STREAM)ass:
444+
try:
445+
s.bind(("",number))
446+
returnTrue
447+
exceptOSError:
448+
returnFalse
449+
439450
# Database control
440451
defdb_connect(self,dbname,user,password=None,host="localhost",port=5432):
441452
conn=pglib.connect(

‎testgres/operations/os_ops.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -127,6 +127,10 @@ def get_pid(self):
127127
defget_process_children(self,pid):
128128
raiseNotImplementedError()
129129

130+
defis_port_free(self,number:int):
131+
asserttype(number)==int# noqa: E721
132+
raiseNotImplementedError()
133+
130134
# Database control
131135
defdb_connect(self,dbname,user,password=None,host="localhost",port=5432):
132136
raiseNotImplementedError()

‎testgres/operations/remote_ops.py

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -629,6 +629,44 @@ def get_process_children(self, pid):
629629

630630
raiseExecUtilException(f"Error in getting process children. Error:{result.stderr}")
631631

632+
defis_port_free(self,number:int)->bool:
633+
asserttype(number)==int# noqa: E721
634+
635+
cmd= ["nc","-w","5","-z","-v","localhost",str(number)]
636+
637+
exit_status,output,error=self.exec_command(cmd=cmd,encoding=get_default_encoding(),ignore_errors=True,verbose=True)
638+
639+
asserttype(output)==str# noqa: E721
640+
asserttype(error)==str# noqa: E721
641+
642+
ifexit_status==0:
643+
return__class__.helper__is_port_free__process_0(output)
644+
645+
ifexit_status==1:
646+
return__class__.helper__is_port_free__process_1(error)
647+
648+
errMsg="nc returns an unknown result code: {0}".format(exit_status)
649+
650+
RaiseError.CommandExecutionError(
651+
cmd=cmd,
652+
exit_code=exit_status,
653+
msg_arg=errMsg,
654+
error=error,
655+
out=output
656+
)
657+
658+
@staticmethod
659+
defhelper__is_port_free__process_0(output:str)->bool:
660+
asserttype(output)==str# noqa: E721
661+
# TODO: check output message
662+
returnFalse
663+
664+
@staticmethod
665+
defhelper__is_port_free__process_1(error:str)->bool:
666+
asserttype(error)==str# noqa: E721
667+
# TODO: check error message
668+
returnTrue
669+
632670
# Database control
633671
defdb_connect(self,dbname,user,password=None,host="localhost",port=5432):
634672
conn=pglib.connect(

‎tests/test_testgres_remote.py

Lines changed: 0 additions & 67 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,6 @@
44
importsubprocess
55

66
importpytest
7-
importpsutil
87
importlogging
98

109
from .helpers.os_ops_descrsimportOsOpsDescrs
@@ -27,8 +26,6 @@
2726
get_pg_config
2827

2928
# NOTE: those are ugly imports
30-
from ..testgresimportbound_ports
31-
from ..testgres.nodeimportProcessProxy
3229

3330

3431
defutil_exists(util):
@@ -259,70 +256,6 @@ def test_unix_sockets(self):
259256
assert (res_exec== [(1,)])
260257
assert (res_psql==b'1\n')
261258

262-
deftest_ports_management(self):
263-
assertbound_portsisnotNone
264-
asserttype(bound_ports)==set# noqa: E721
265-
266-
iflen(bound_ports)!=0:
267-
logging.warning("bound_ports is not empty: {0}".format(bound_ports))
268-
269-
stage0__bound_ports=bound_ports.copy()
270-
271-
with__class__.helper__get_node()asnode:
272-
assertbound_portsisnotNone
273-
asserttype(bound_ports)==set# noqa: E721
274-
275-
assertnode.portisnotNone
276-
asserttype(node.port)==int# noqa: E721
277-
278-
logging.info("node port is {0}".format(node.port))
279-
280-
assertnode.portinbound_ports
281-
assertnode.portnotinstage0__bound_ports
282-
283-
assertstage0__bound_ports<=bound_ports
284-
assertlen(stage0__bound_ports)+1==len(bound_ports)
285-
286-
stage1__bound_ports=stage0__bound_ports.copy()
287-
stage1__bound_ports.add(node.port)
288-
289-
assertstage1__bound_ports==bound_ports
290-
291-
# check that port has been freed successfully
292-
assertbound_portsisnotNone
293-
asserttype(bound_ports)==set# noqa: E721
294-
assertbound_ports==stage0__bound_ports
295-
296-
# TODO: Why does not this test work with remote host?
297-
deftest_child_process_dies(self):
298-
nAttempt=0
299-
300-
whileTrue:
301-
ifnAttempt==5:
302-
raiseException("Max attempt number is exceed.")
303-
304-
nAttempt+=1
305-
306-
logging.info("Attempt #{0}".format(nAttempt))
307-
308-
# test for FileNotFound exception during child_processes() function
309-
withsubprocess.Popen(["sleep","60"])asprocess:
310-
r=process.poll()
311-
312-
ifrisnotNone:
313-
logging.warning("process.pool() returns an unexpected result: {0}.".format(r))
314-
continue
315-
316-
assertrisNone
317-
# collect list of processes currently running
318-
children=psutil.Process(os.getpid()).children()
319-
# kill a process, so received children dictionary becomes invalid
320-
process.kill()
321-
process.wait()
322-
# try to handle children list -- missing processes will have ptype "ProcessType.Unknown"
323-
[ProcessProxy(p)forpinchildren]
324-
break
325-
326259
@staticmethod
327260
defhelper__get_node(name=None):
328261
assertisinstance(__class__.sm_os_ops,OsOperations)

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp