2008-09-05 21 views
56

Si usó Oracle, probablemente haya recibido el mensaje útil "ORA-00942: la tabla o vista no existe". ¿Existe una razón técnica legítima por la cual el mensaje no incluye el nombre del objeto faltante?¿Por qué Oracle no te dice CUÁL tabla o vista no existe?

Los argumentos acerca de este ser debido a la seguridad de sonido como si estuvieran hechos a mano por la TSA. Si soy un atacante, sabría qué tabla intenté explotar y podría interpretar fácilmente este mensaje inútil. Si soy un desarrollador que trabaja con una unión compleja a través de varias capas de código de aplicación, a menudo es muy difícil de decir.

Mi conjetura es que cuando se implementó originalmente este error, alguien se olvidó de añadir el nombre del objeto, y ahora, la gente tiene miedo que se rompa la compatibilidad para solucionarlo. (El código haciendo cosas tontas como analizar el mensaje de error se confundirá si cambia).

¿Existe alguna forma amigable para el desarrollador (en lugar de reclutar a su DBA) para determinar el nombre de la tabla faltante?


Aunque he aceptado una respuesta que es relevante para el tema, que en realidad no responde a mi pregunta: ¿Por qué no es la parte del nombre del mensaje de error? Si alguien puede encontrar la respuesta real, me complacerá cambiar mi voto.

+1

Imagino que tendría que pedirle a un ingeniero de Oracle real que obtenga la respuesta real. Por cierto, yo trabajo para Sybase, y nuestro servidor (SQL Anywhere) te da "Tabla 'blah' no encontrada". –

+3

Puede deberse a un reflejo de no divulgación;): [enlace] (http://www.cloudave.com/13729/amazon-google-facebook-microsoft-apple-and-oracle-org-chart/) –

+7

Bueno, estoy totalmente de acuerdo con el póster. Me ha costado horas tratar de encontrar problemas de desarrollo porque oráculo se niega a decir qué tabla no existía. ¿Y seguridad? ¡Aún puede optar por NO pasarle al cliente el mensaje de error detallado que NUNCA suele hacer! Normalmente me parece que el software de Oracle es muy malo cuando se trata de pensar un poco más allá de lo obvio ... – Lawrence

Respuesta

13

Puede establecer un EVENTO en su archivo de parámetros (texto plano o spfile) para forzar a Oracle a volcar un archivo de rastreo detallado en el user_dump_dest, el nombre del objeto podría estar allí, si no el SQL.

EVENTO = "942 nombre de la traza nivel errorstack 12"

Si está utilizando un archivo de texto sin formato que necesita para mantener todas sus configuraciones evento sobre líneas consecutivas. No estoy seguro de cómo se aplica a spfile.

+0

Intenté agregar esta línea al archivo "init.ora", luego reinicié mi dbms, pero no había nada disponible en la carpeta user_dump_dest. Cualquier consejo, por favor? –

5

Si está utilizando una herramienta de navegación SQL como las salchichas o TORA que le ayudará con errores ORA por highlightling o señalar moviendo el cursor a donde hizo su error.

Copiar y pegar el SQL en una de estas herramientas para ayudar. También puede encontrar útil la información de análisis disponible.

+0

Bueno, para mí está resaltando una constante que he definido, p. ": myvar" así que no hay ayuda en absoluto, entonces –

4

Si no es una declaración enorme, entonces la manera más fácil es sólo para comprobar el diccionario de datos,

SQL> select * from xx,abc; 
select * from xx,abc 
       * 
ERROR at line 1: 
ORA-00942: table or view does not exist 


SQL> select owner,table_name from all_tables where table_name in ('XX','ABC'); 

OWNER       TABLE_NAME 
------------------------------ ------------------------------ 
MWATSON      XX 

SQL> 

Esto no es ideal, pero corto de ida y el examen de los archivos de seguimiento, no estoy seguro ¿De qué otra manera hacerlo?

2

@Matthew

Su consulta es un comienzo, pero podría no funcionar cuando se tienen varios esquemas. Por ejemplo, si inicio sesión en nuestra instancia como yo mismo, he leído el acceso a todas nuestras tablas. Pero si yo no califico el nombre de tabla con el esquema voy a conseguir un ORA-00942 para las tablas sin sinónimos:

 
SQL> select * from tools; 
select * from tools 
       * 
ERROR at line 1: 
ORA-00942: table or view does not exist 

La tabla sigue apareciendo en all_tables sin embargo:

 
SQL> select owner, table_name from all_tables where table_name = 'TOOLS'; 

OWNER       TABLE_NAME 
------------------------------ ------------------------------ 
APPLICATION     TOOLS 

@ erikson Lo siento, eso no ayuda mucho. Estoy con Mark, usé TOAD.

13

SQL * Plus le indica la tabla que no existe.Por ejemplo:

SQL> select 
    2  * 
    3 from 
    4  user_tables a, 
    5  non_existent_table b 
    6 where 
    7  a.table_name = b.table_name; 
    non_existent_table b 
    * 
ERROR at line 5: 
ORA-00942: table or view does not exist 

Aquí se muestra el nombre de la tabla que falta y el número de línea en la declaración de SQL donde se produce el error.

Del mismo modo, en una sentencia SQL de una línea se puede ver el asterisco destacando el nombre de la tabla desconocido:

SQL> select * from user_tables a, non_existent_table b where a.table_name = b.table_name; 
select * from user_tables a, non_existent_table b where a.table_name = b.table_name 
          * 
ERROR at line 1: 
ORA-00942: table or view does not exist 

En cuanto a su pregunta, supongo que la razón el mensaje de error no incluye el nombre de la tabla es que el mensaje de error en sí debe ser texto estático. El número de línea y la ubicación en la línea del error se pasan claramente a SQL * Plus (de alguna manera).

+5

Esto está bien cuando puede usar SQL * Plus de manera interactiva para probar sus consultas. Un caso común, sin embargo, es cuando solo tiene un registro de una aplicación que utiliza una capa de persistencia como Hibernate y es difícil correlacionar exactamente qué consulta se pudo haber ejecutado. – erickson

+2

@erickson: eso es más un problema con Hibernate;) (Es una broma) –

+2

@erickson: Me temo que es una limitación del delgado controlador JDBC. OCI llamada OCIErrorGet puede devolver más de una cadena de error. El primero es principal, los demás son detalles (como un stacktrace). También puede solicitar un "identificador de error" para obtener detalles como OCI_ATTR_PARSE_ERROR_OFFSET. No encuentro ninguna llamada de corrección en la API del controlador JDBC. De todos modos, el controlador Oracle JDBC arroja JDBC SqlExption genérico puro, nada específico de Oracle. – ibre5041

5

Nunca he tenido un problema con la interpretación de los mensajes de error de Oracle. Parte de la razón es que cada herramienta interactiva que he visto para desarrollar SQL para Oracle apunta útilmente a la ubicación incorrecta de la consulta. Eso incluye SQL * Plus, como otros han observado, y el módulo Perl DBI:

$ exec_sql.pl 'select * from daul' 
DBD::Oracle::db prepare failed: ORA-00942: table or view does not exist (DBD ERROR: error possibly near <*> indicator at char 14 in 'select * from <*>daul') [for Statement "select * from daul"] at exec_sql.pl line 68. 

Bueno, eso es un poco difícil de leer, ya que todo está deformado en una línea. Pero una herramienta de GUI podría apuntar al token donde Oracle comenzó a tener problemas con la consulta. Y dado un poco de trabajo en un analizador sintáctico, podría escribir una herramienta para seleccionar la tabla ofensiva.

Para responder a la pregunta subyacente, los errores de Oracle no parecen estar diseñados para funcionar de la manera esperada. Por lo que puedo decir, ninguno de los mensajes de error en Oracle admite texto variable. En cambio, Oracle devuelve dos bits de información: un número de error y una ubicación donde se produce el error. Si tiene las herramientas adecuadas, es bastante fácil diagnosticar un error con esos datos. Se puede argumentar que el sistema de Oracle es más agradable para los creadores de herramientas que uno que proporciona cantidades variables de datos de diagnóstico según el error. Imagine tener que escribir un analizador personalizado para todos los mensajes de error de Oracle (incluidos los errores futuros) para resaltar la ubicación ofensiva.

A veces, incluir el nombre de la tabla sería engañoso. El hecho de saber que las cosas iban mal puede ser de gran ayuda:

SQL> select * from where dummy = 'X'; 
select * from where dummy = 'X' 
       * 
ERROR at line 1: 
ORA-00903: invalid table name 

cuanto a por qué Oracle eligió hacer algo así, tengo algunas especulaciones:

  1. IBM utiliza este tipo de mensaje de error para Sistema R, que Larry Ellison, Bob Miner y Ed Oates copiaron para construir Oracle V2. (Compatibilidad con versiones anteriores)

  2. El número de error y la ubicación son la representación más pequeña posible de la información de diagnóstico. (Parsimony.)

  3. Como indiqué anteriormente, para simplificar la creación de herramientas que se conectan a Oracle. (Interoperabilidad)

En cualquier caso, no creo que deba ser un DBA para averiguar qué tabla no existe. Solo necesitas usar las herramientas adecuadas. (Y ajustar sus expectativas, supongo.)

+1

Gracias por la entrada de Jon. No lo dejé claro, pero en mi caso, estos se encuentran normalmente en las aplicaciones Java a través de varias capas diferentes de código ... un marco web, una biblioteca de persistencia, el controlador de la base de datos Java. Por lo tanto, puede ser difícil a veces incluso determinar qué consulta se estaba ejecutando, especialmente si está trabajando con otro grupo para obtener registros creados durante la prueba por un tercer grupo. Sí, es un verdadero barril de monos. – erickson

+0

Diría que eso es más una acusación de Java que Oracle. ;-) –

+1

Muy cierto. Pero nunca traté de acusar a Oracle ... a menos que cuentes que JAVA es ORCL. A pesar de algunas peculiaridades, Oracle es excelente en términos absolutos, y alineado al lado de la "competencia" se ve aún mejor. – erickson

3

Razón 1: Interfaz multilingüe

Hay un archivo de configuración de avisos lenguaje específico para la instancia de base de datos.Los mensajes se extraen de allí y se traducen de la versión numérica pura a la versión numérica + texto.

Probablemente se consideró mejor tener las cadenas codificadas, que correr el riesgo en el tiempo de ejecución de tener una falla misteriosa debido a una cadena "% s" mal formateada.

(. No es que yo particularmente estoy de acuerdo con este Punto de vista, por cierto)

Razón 2: Seguridad

En este momento usted particularmente no expone el funcionamiento interno de su aplicación si se imprime un PHP , etc., volcado de un mensaje de error de Oracle en el navegador.

Las aplicaciones estarían un poco más expuestas si se imprimieran más detalles por defecto ... Por ejemplo, si citibank imprimió un mensaje más explicativo.

(ver aviso legal anterior, yo sería feliz para obtener más información en el error también.)

+0

[' ORA-00932 tipos de datos inconsistentes:% esperado s obtuvo% s'] (http://docs.oracle.com/cd/B10501_01/server.920/a96525/e900.htm#206194) –

5

estoy de acuerdo con la opinión, de que SQL + le permite entender qué nombre de la tabla es inaceptable. Es cierto que ayuda en DML directo, aunque el análisis es muy difícil. Pero cuando se trata de dinámica, no obtenemos ayuda:

SQL> begin 
    2 execute immediate 'insert into blabla values(1)'; 
    3 end; 
    4/
begin 
* 
ERROR at line 1: 
ORA-00942: table or view does not exist 
ORA-06512: at line 2 
Cuestiones relacionadas