Bonjour,

Voici mon problème:

j'ai dans ma base de données une table qui crée une arborescence, je gère ce lien avec un champ idParent, qui contient null si la Famille est au sommet de l'arborescence, qui contient l'id de son supérieur dans le cas contraire.

Voici le script de création de cette table :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
CREATE TABLE Family (
	id numeric IDENTITY,
	shortName varchar(30),
	fullName varchar(80),
	[GroupofFamily.id] numeric,
	[ColorofFamily.id] numeric,
	idParent numeric,
	PRIMARY KEY (id),
	FOREIGN KEY ([GroupofFamily.id]) REFERENCES GroupofFamily(id),
	FOREIGN KEY ([ColorofFamily.id]) REFERENCES ColorofFamily(id)
)
Cette famille a un lien avec avec deux autres tables, que j'ai initialisé avec des valeurs bidons pour mes tests.

J'ai donc rempli cette table de cette manière :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
insert into Family (shortName, fullName, [GroupofFamily.id], [ColorofFamily.id], idParent) values ('1','1',1,1,null),
('1.1','1.1',1,1,1),
('1.2','1.2',1,1,1),
('1.3','1.3',1,1,1),
('1.2.1','1.2.1',1,1,3),
('1.2.2','1.2.2',1,1,3),
('1.2.3','1.2.3',1,1,3),
('2','2',1,1,null),
('1.2.3.1','1.2.3.1',1,1,7),
('1.2.3.2','1.2.3.2',1,1,7),
('1.2.3.1.1','1.2.3.1.1',1,1,9),
('1.2.3.1.2','1.2.3.1.2',1,1,9);
ce qui donne :
1
1.1
1.2
1.2.1
1.2.2
1.2.3
1.2.3.1
1.2.3.1.1
1.2.3.1.2
1.2.3.2
2
J'ai tenté de créer une procédure pour supprimer proprement mon arborescence, sans laisser de branche orpheline :

Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
CREATE PROCEDURE Family_Delete @idToDelete numeric
AS
BEGIN
	DECLARE @idBuf numeric
	DECLARE @idToScan numeric
	DECLARE id_cursor CURSOR LOCAL FOR (select id from Family where idParent = @idToDelete)
 
	open id_cursor
	fetch next from id_cursor into @idToScan
 
	while @@FETCH_STATUS = 0
	begin
		set @idBuf = (select id from Family where idParent = @idToScan)
		if @idBuf is null
		begin
			set @idBuf = (select idParent from Family where id = @idToScan)
			delete from Family where id = @idToScan
			if @idBuf is not null 
			begin
				execute Family_Delete @idBuf
			end
		end
		else
		begin
			execute Family_Delete @idToScan
		end
 
		fetch next from id_cursor into @idToScan
	end
	delete from Family where id = @idToDelete
 
	close id_cursor
	DEALLOCATE id_cursor
END
go
Problème :
J'essaye de supprimer la branche 1.2 :
lorsque mon arborescence dépasse le stade 1.2.3, cela m'affiche ce message d'erreur :
Subquery returned more than 1 value. This is not permitted when the subquery follows =, !=, <, <= , >, >= or when the subquery is used as an expression.
Dans les autres cas je n'ai pas d'erreur et la suppression se fait sans problème.

Ce message concerne la ligne où je déclare mon curseur.
Je ne comprend pas pourquoi j'ai ce message puisque je fais appel à Family_Delete uniquement par le biais de @idToScan ou idBuf.
Or @idToScan ne contient qu'une seule valeur puisque que son contenu vient de mon curseur, et @idBuf ne peut contenir *normalement* qu'un résultat puisque la condition est "where id = ..." et que le champ id est l'identifiant de ma table (donc unique)

Je ne vois pas où est mon erreur

Voici l'état de ma table avant exécution :


et après :