Bonjour,

Je fais face à un léger problème lors de l'utilisation de l'API DBMS_XMLStore.
En effet toute opération d'insertion/update via un synonyme portant sur une table présente schéma présent sur la même instance que celle du schéma depuis lequel la procédure stockée est invoquée.
La procédure se déroule sans le moindre problème (pas d'exception levée), mais au final aucune ligne n'est insérée dans la table sur laquelle pointe le synonyme.
Les grants en insert/update sont bien positionnés au niveau de la table cible, de même pour le synonyme pour mon user.
La même procédure fonctionne de la façon voulue si l'on cible une table du schéma local.


Le code ressemble à ceci (carrément pas original et rien de touchy, et puis je skippe un paquet de colonnes)

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
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
 
create or replace
PROCEDURE ps_test_insert_cp(p_xml_in varchar2 ) AS
  v_context DBMS_XMLStore.ctxType;
  v_xml_doc XMLType;
  v_rows NUMBER;
  lc$id varchar(100);
  row_xml XMLType;
  nb_row NUMBER;
  x NUMBER;
 
  CURSOR crsrNodeList(cv_doc XMLType, cv_path VARCHAR2) IS
  SELECT XMLSequence(extract(cv_doc,cv_path)) XML
  FROM dual;
 
  nodelist xmlsequencetype;
  sea varchar(100);
BEGIN
  v_xml_doc := XMLType(p_xml_in);
  --
  -- Count the number records in ROWSET/ROW
  --
 
   OPEN  crsrNodeList(v_xml_doc,'//*/ROW');
   FETCH crsrNodeList INTO nodeList;
   CLOSE crsrNodeList;
   nb_row := nodelist.count();
   dbms_output.put_line( 'Number of records=' || nb_row );
 
  --
  -- Loop thru the records
  --
 
    FOR x IN 1 .. nb_row LOOP
 
      sea := '/ROWSET/ROW['|| to_char(x) || ']';
      row_xml := v_xml_doc.extract(sea);
      dbms_output.put_line( 'XML Subtree=' || row_xml.getClobVal );
 
      lc$id := row_xml.extract('/ROW/COL1/text()').getStringVal ;
      select count(*)
      into v_rows
      from CEO_TEST
      where ID = lc$id;
 
      -- Build the XMLStore Content and update or insert      
 
      v_context := DBMS_XMLStore.newContext('TEST');
      DBMS_XMLStore.setUpdateColumn(v_context,'COL1');
      DBMS_XMLStore.setUpdateColumn(v_context,'COL2');
      ...
      IF v_rows = 0 THEN
         dbms_output.put_line('v_rows='||v_rows);
         dbms_output.put_line('insert');
         v_rows := DBMS_XMLStore.insertXML(v_context, row_xml);
         dbms_output.put_line('v_rows='||v_rows);        
      ELSE
         dbms_output.put_line('update');
         DBMS_XMLStore.setKeyColumn(v_context, 'COL1');
         v_rows := DBMS_XMLStore.updateXML(v_context, row_xml);
      END IF;
      DBMS_XMLStore.closeContext(v_context);
  END LOOP;
  commit;
END;

Pour la table , dans le genre bidon on fait pas mieux
Code : Sélectionner tout - Visualiser dans une fenêtre à part
CREATE TABLE TEST (COL1 VARCHAR2(10),COL2 VARCHAR2(10))
le XML associé

Code : Sélectionner tout - Visualiser dans une fenêtre à part
<ROWSET><ROW><COL1>truc</COL1><COL2>Machin</COL2></ROW></ROWSET>
Bon par contre faut avoir deux schemas sous la main, les grants adequats et créer le synonyme, si besoin est je fournirais les scripts associés.

Donc si vous aviez une idée de ce que j'ai mal foutu (je suis sûr que c'est une connerie, et l'unique DBA qui ne soit pas en vacances est un guignol) au niveau droits ou que ne sais-je encore, j'apprécierais amplement de me faire botter le cul

Merci d'avance pour le coup de main
@+