diff --git a/testsuite/pytests/sli2py_regressions/test_issue_665.py b/testsuite/pytests/sli2py_regressions/test_issue_665.py
new file mode 100644
index 0000000000..1acc10bcf1
--- /dev/null
+++ b/testsuite/pytests/sli2py_regressions/test_issue_665.py
@@ -0,0 +1,95 @@
+# -*- coding: utf-8 -*-
+#
+# test_issue_665.py
+#
+# This file is part of NEST.
+#
+# Copyright (C) 2004 The NEST Initiative
+#
+# NEST is free software: you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation, either version 2 of the License, or
+# (at your option) any later version.
+#
+# NEST is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with NEST. If not, see .
+
+"""
+Regression test for Issue #665 (GitHub).
+
+This test ensures that ConnectLayers correctly handles devices with thread
+siblings as sources and targets.
+
+See also
+- https://github.com/nest/nest-simulator/issues/665
+- https://github.com/nest/nest-simulator/pull/666
+"""
+
+import nest
+import pytest
+
+pytestmark = pytest.mark.skipif_missing_threads
+
+
+@pytest.fixture(autouse=True)
+def reset_kernel():
+ nest.ResetKernel()
+
+
+@pytest.mark.parametrize(
+ "connspec",
+ [
+ {"rule": "pairwise_bernoulli", "p": 1, "use_on_source": True},
+ {"rule": "pairwise_bernoulli", "p": 1, "use_on_source": False},
+ {"rule": "fixed_outdegree", "outdegree": 4, "allow_multapses": False},
+ ],
+)
+def test_connect_generator_layer(connspec):
+ """
+ Confirm that devices can be connected as sources to layers with arbitrary connection rules.
+ Each neuron should appear exactly once as a connection target.
+ """
+
+ nest.local_num_threads = 4
+
+ gen_layer = nest.Create("poisson_generator", positions=nest.spatial.grid(shape=[1, 1]))
+ nrn_layer = nest.Create("parrot_neuron", positions=nest.spatial.grid(shape=[2, 2]))
+
+ nest.Connect(gen_layer, nrn_layer, connspec)
+ conns = nest.GetConnections(source=gen_layer).get("target")
+
+ assert sorted(conns) == list(nrn_layer.global_id)
+
+
+@pytest.mark.parametrize(
+ "connspec,pass_expected",
+ [
+ [{"rule": "pairwise_bernoulli", "p": 1, "use_on_source": True}, True],
+ [{"rule": "pairwise_bernoulli", "p": 1, "use_on_source": False}, False],
+ [{"rule": "fixed_indegree", "indegree": 4, "allow_multapses": False}, False],
+ ],
+)
+def test_connect_recorder_layer(connspec, pass_expected):
+ """
+ Confirm that neurons can be connected to a recorder with pairwise bernoulli used on source.
+ Other connection rules shall trigger an error. If connections are created, each neuron shall
+ appear exactly once as a connection source.
+ """
+
+ nest.local_num_threads = 4
+
+ nrn_layer = nest.Create("parrot_neuron", positions=nest.spatial.grid(shape=[2, 2]))
+ rec_layer = nest.Create("spike_recorder", positions=nest.spatial.grid(shape=[1, 1]))
+
+ if pass_expected:
+ nest.Connect(nrn_layer, rec_layer, connspec)
+ conns = nest.GetConnections(target=rec_layer).get("source")
+ assert sorted(conns) == list(nrn_layer.global_id)
+ else:
+ with pytest.raises(nest.kernel.NESTErrors.IllegalConnection):
+ nest.Connect(nrn_layer, rec_layer, connspec)
diff --git a/testsuite/regressiontests/issue-665.sli b/testsuite/regressiontests/issue-665.sli
deleted file mode 100644
index 6117697dfc..0000000000
--- a/testsuite/regressiontests/issue-665.sli
+++ /dev/null
@@ -1,160 +0,0 @@
-/*
- * issue-665.sli
- *
- * This file is part of NEST.
- *
- * Copyright (C) 2004 The NEST Initiative
- *
- * NEST is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 2 of the License, or
- * (at your option) any later version.
- *
- * NEST is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with NEST. If not, see .
- *
- */
-
-
- /** @BeginDocumentation
-Name: testsuite::issue-665
-
-Synopsis: (issue-665) run -> NEST exits if test fails
-
-Description:
-This test ensures that ConnectLayers correctly handles devices with thread
-siblings as sources and targets.
-
-Author: Hans Ekkehard Plesser
-FirstVersion: February 2017
-SeeAlso:
-*/
-
-(unittest) run
-/unittest using
-
-skip_if_not_threaded
-
-% First set of tests: Single generator to neuron layer
-/gen_to_layer_test
-{
- /connspec Set
-
- ResetKernel
- << /local_num_threads 4 >> SetKernelStatus
-
- /pgl
- << /elements /poisson_generator
- /shape [ 1 1 ] >>
- CreateLayer def
-
- /nnl
- << /elements /iaf_psc_alpha
- /shape [ 2 2 ] >>
- CreateLayer def
-
- pgl nnl connspec ConnectLayers
-
- /src pgl [1] Take def
- /tgts nnl def
-
- /conns << /source src >> GetConnections def
- /ctgts conns { cva 1 get } Map Sort def
-
- tgts cva ctgts eq
-}
-def
-
-{
- << /connection_type /pairwise_bernoulli_on_source >> gen_to_layer_test
-}
-assert_or_die
-
-{
- << /connection_type /pairwise_bernoulli_on_target >> gen_to_layer_test
-}
-assert_or_die
-
-{
- % one incoming connection to each neuron in layer
- << /connection_type /pairwise_bernoulli_on_source
- /number_of_connections 1 >> gen_to_layer_test
-}
-assert_or_die
-
-{
- % four outgoing connections, one to each neuron in layer
- % prohibit multapses to ensure consistent result
- << /connection_type /pairwise_bernoulli_on_target
- /number_of_connections 4
- /allow_multapses false >> gen_to_layer_test
-}
-assert_or_die
-
-% -----------------------------------------------
-
-% Second set of tests: Neuron layer to single recorder
-/layer_to_det_test
-{
- /connspec Set
-
- ResetKernel
- << /local_num_threads 4 >> SetKernelStatus
-
- /nnl
- << /elements /iaf_psc_alpha
- /shape [ 2 2 ] >>
- CreateLayer def
-
- /srl
- << /elements /spike_recorder
- /shape [ 1 1 ] >>
- CreateLayer def
-
- nnl srl connspec ConnectLayers
-
- /tgt srl [1] Take def
- /srcs nnl def
-
- /conns << /target tgt >> GetConnections def
- /csrcs conns { cva 0 get } Map Sort def
-
- srcs cva csrcs eq
-}
-def
-
-{
- << /connection_type /pairwise_bernoulli_on_source >> layer_to_det_test
-}
-assert_or_die
-
-{
- << /connection_type /pairwise_bernoulli_on_target >> layer_to_det_test
-}
-fail_or_die
-clear
-
-{
- % four incoming connections, one to each neuron in layer
- % prohibit multapses to ensure consistent result
- << /connection_type /pairwise_bernoulli_on_source
- /number_of_connections 4
- /allow_multapses false >> layer_to_det_test
-}
-fail_or_die
-clear
-
-{
- % one outgoing connection from each neuron in layer
- << /connection_type /pairwise_bernoulli_on_target
- /number_of_connections 1 >> layer_to_det_test
-}
-fail_or_die
-clear
-
-endusing