2012-03-29 15 views
5

Tengo un tipo de objeto con constructor no-args, pero cuando lo especifico como valor predeterminado para una columna de ese tipo, obtengo ORA-00904: error de identificador no válido.Oracle: especificar el valor predeterminado para la columna de tipo de objeto

Ejemplo:

 
CREATE OR REPLACE TYPE test_t AS OBJECT 
(
    val  NUMBER(10), 
    CONSTRUCTOR FUNCTION test_t return self as result 
) 

CREATE OR REPLACE TYPE BODY test_t AS 
    CONSTRUCTOR FUNCTION test_t RETURN SELF AS RESULT IS 
    BEGIN 
    val := 1; 
    RETURN; 
    END; 
END; 

CREATE TABLE test_table (
    test_attr test_t DEFAULT new test_t() 
) 

Error: ORA-00904: "INKA"."TEST_T"."TEST_T": invalid identifier 

Si sustituyo DEFAULT con, por ejemplo test_t (1), funciona, pero eso rompe el paradigma de encapsulación OO, quiero que todos los campos del mismo tipo tengan los mismos "valores predeterminados" predeterminados (espero que sepas lo que quiero decir :-)

Me falta algo aquí, o es esto normal y no es posible usar constructores no predeterminados como este?

Respuesta

0

Parece que esto no es posible.

Una solución sería utilizar un disparador:

CREATE OR REPLACE TRIGGER test_trigger 
    BEFORE INSERT OR UPDATE 
ON test_table 
    FOR EACH ROW 
WHEN (new.test_attr IS NULL) 
BEGIN 
    :new.test_attr := NEW test_t(); 
END test_trigger; 
/

No ignora por completo constructores no predeterminados por cierto, anulando el constructor por defecto

CONSTRUCTOR FUNCTION test_t(in_val NUMBER) 
RETURN SELF AS RESULT 

conduce a una excepción al tratar de definir la tabla con DEFAULT NEW test_t(1):

ORA-06553: PLS-307: demasiadas declaraciones de 'TEST_T' coinciden con esta llamada

+0

ORA-06553: PLS-307 es resultado de la definición del constructor duplicado, Oracle es algo gracioso en eso; si reemplaza el nombre del parámetro "in_val" con val (como es el nombre del atributo), anulará correctamente el constructor predeterminado. –

+0

Correcto, pero aún encuentra este constructor ... –

+0

Conozco la solución de desencadenante, pero 5-10 líneas de código para algo que debería ser posible de una manera mucho más legible y manejable. Inicialmente, supuse que no era posible porque el contexto de SQL no se ve dentro del contexto PL/SQL, pero claramente no es el caso, ya que ninguna de las cosas OO funcionaría en SQL puro. Entonces, este problema es un descuido por parte de Oracle, o hay alguna sintaxis que desconozco ... –

Cuestiones relacionadas