java preferences

Java: java.util.Preferences Fallando



(10)

Desafortunadamente, la mayoría de las respuestas que obtuviste están equivocadas ... al menos ligeramente. En el sentido de que el síntoma está siendo tratado, no la causa.

Recapitulemos. Las Preferencias de Java tienen dos "árboles": el árbol de usuarios y el árbol del sistema . Puede escribir su propio backend en las Preferencias de Java (llamado almacén de respaldo) pero pocos desarrolladores lo hacen, por lo que termina con el almacén de respaldo predeterminado de JDK. En una plataforma Windows, esto significa el Registro de Windows, más específicamente:

  • El árbol de usuarios está escrito en HKEY_CURRENT_USER/Software/JavaSoft/Prefs (el usuario del sistema operativo siempre tiene acceso de escritura aquí)
  • El árbol del sistema está escrito en HKEY_LOCAL_MACHINE/Software/JavaSoft/Prefs (solo un usuario del sistema operativo con privilegios de administrador tiene acceso de escritura aquí)

En resumen: siempre que su código no intente utilizar el árbol del sistema, debería estar bien y no debería tener que meterse en la asignación de privilegios en el nivel del sistema operativo. El árbol del sistema está destinado a "todos los usuarios en el host" y el árbol de usuarios está destinado al usuario que ha iniciado sesión específicamente. En su caso, estoy seguro de que puede bastar con el árbol de usuarios, de modo que esa es realmente su solución. No juegue con privilegios, ejecute como administrador, y qué no.

.... pero hay más. Supongamos que su código no toca deliberadamente el árbol del sistema de Preferencias de Java, como se indica. A continuación, seguirá viendo esta advertencia en Windows:

WARNING [java.util.prefs]: Could not open/create prefs root node Software/JavaSoft/Prefs at root 0x80000002. Windows RegCreateKeyEx(...) returned error code 5.

¿Entonces qué está pasando? ¿Te di el consejo equivocado? Realmente no. Quédate conmigo.

Al sumergirse en el código fuente de JDK, verá que 0x80000002 significa HKLM, es decir, el lugar en el Registro de Windows que no se debe tocar. ¡Tu código nunca hace referencia al árbol del sistema y aún así ves esta advertencia! (En este punto, debes arrancarte todo el pelo ... como lo hice)

Bueno, esta es una de las raras ocasiones en que realmente hay un error JDK . Puede leer más sobre esto en esta respuesta , que le recomiendo que lea si está interesado en saber por qué los errores sutiles pueden pasar desapercibidos en el JDK durante años. El error ha existido desde JDK 1.4, pero solo recientemente se ha corregido y aún no se ha cargado a JDK 8.

Mejor consejo

  • Asegúrese de que su código solo haga referencia al árbol de usuarios, no al árbol del sistema. Es justo que el sistema operativo requiera todo tipo de privilegios para que escriba en una ubicación de todo el sistema. Si realmente necesita escribir en tal ubicación, entonces realmente no hay otra solución que asignar privilegios, ejecutando como Administrador o lo que no.
  • Ignora la advertencia. Desaparecerá una vez que esté en Java 9 o cuando Oracle decida volver a instalar la corrección de errores en Java 8. La advertencia puede ignorarse de forma segura.
  • Alternativamente, puede intentar ignorar la advertencia mediante programación. Viene del Platform Logger del JDK, así que algo como esto debería funcionar, aunque no lo he probado yo mismo:

    sun.util.logging.PlatformLogger platformLogger = PlatformLogger.getLogger("java.util.prefs"); platformLogger.setLevel(PlatformLogger.Level.OFF);

Mi programa guarda los datos de clave de producto encriptados en la computadora con la clase java.util.Preferences (preferencias del sistema, no usuario). El problema es que, tanto en Windows como en Linux (no lo he probado en OSX, pero probablemente sea el mismo), si no ejecuto el programa con sudo o con privilegios de administrador, emite una excepción o advertencia cuando intenta leer. o guardar los datos.

Obviamente, requerir que el usuario ejecute el programa con privilegios de administrador no sería práctico. De manera óptima, me gustaría que el sistema operativo le pidiera permiso al usuario.

Esto es bastante tonto y elimina la mitad del propósito de las Preferences . ¿Cómo se puede arreglar esto?

Aquí hay un resumen de lo que necesito : necesito que mi programa solicite permiso al sistema operativo para guardar la configuración del sistema.

Aquí está la información del error.

Aquí está el error cuando intento leer un nodo (porque el nodo no existe):

Mar 18, 2011 9:41:15 AM java.util.prefs.WindowsPreferences <init> WARNING: Could not create windows registry node Software/JavaSoft/Prefs/myapp at root 0x80000002. Windows RegCreateKeyEx(...) returned error code 5. Mar 18, 2011 9:41:15 AM java.util.prefs.WindowsPreferences WindowsRegOpenKey1 WARNING: Trying to recreate Windows registry node Software/JavaSoft/Prefs/myapp at root 0x80000002. Mar 18, 2011 9:41:15 AM java.util.prefs.WindowsPreferences openKey WARNING: Could not open windows registry node Software/JavaSoft/Prefs/myapp at root 0x80000002. Windows RegOpenKey(...) returned error code 2. Mar 18, 2011 9:41:15 AM java.util.prefs.WindowsPreferences WindowsRegOpenKey1 WARNING: Trying to recreate Windows registry node Software/JavaSoft/Prefs/myapp/subpackage at root 0x80000002. Mar 18, 2011 9:41:15 AM java.util.prefs.WindowsPreferences openKey WARNING: Could not open windows registry node Software/JavaSoft/Prefs/myapp/subpackage at root 0x80000002. Windows RegOpenKey(...) returned error code 2.

Y esto es lo que sucede cuando intento escribir en un nodo:

Mar 18, 2011 9:43:11 AM java.util.prefs.WindowsPreferences WindowsRegOpenKey1 WARNING: Trying to recreate Windows registry node Software/JavaSoft/Prefs/myapp/subpackage at root 0x80000002. Mar 18, 2011 9:43:11 AM java.util.prefs.WindowsPreferences openKey WARNING: Could not open windows registry node Software/JavaSoft/Prefs/myapp/subpackage at root 0x80000002. Windows RegOpenKey(...) returned error code 2.


Es posible cambiar los derechos de acceso de las entradas de registro. Si permite derechos de acceso total a HKEY_LOCAL_MACHINE/SOFTWARE/JavaSoft/Prefs para todos, todos verán el mismo conjunto de preferencias y todos podrán cambiarlos globalmente. Soy consciente de que esta no es una solución para el software que instalan los clientes, pero podría ser útil para alguien.


Especialmente con Windows 7, la JVM no tiene de forma predeterminada el permiso para escribir en el registro de Windows donde se encuentra el almacén de respaldo para java.util.prefs.preferences en MS-Windows.

Al ejecutar el transformador ReverseXSL, o incluso el programa de prueba Regex, se pueden obtener errores como: No se pudo abrir / crear preferencias nodo raíz Software / JavaSoft / Prefs en la raíz 0x80000002. Windows RegCreateKeyEx

Esto evita el registro de una licencia. No impide que el software realice transformaciones en el modo de software libre.

Arreglar el problema es simplemente una cuestión de otorgar los permisos necesarios a la clave raíz del registro en juego.

Ejecute regedit.exe como administrador (regedit.exe se encuentra en el directorio raíz del sistema operativo c: / Windows). Vaya a la clave HKEY_LOCAL_MACHINE / SOFTWARE / JavaSoft / Prefs. Haga clic derecho para establecer permisos. Marque una marca en la casilla de verificación Control total para los usuarios que necesitan ejecutar el software reverseXSL.


Este link es trabajo para mí:

Resolver el problema La solución es iniciar sesión como administrator y crear la clave HKEY_LOCAL_MACHINE/Software/JavaSoft/Prefs


La solución es ejecutar JMeter como administrador, creará la clave de registro para usted, luego puede reiniciar JMeter como usuario normal y ya no tendrá la advertencia. Sitio oficial de JMeter - cambios


La solución para mí no era obvia: era actualizar mis archivos de seguridad de criptografía de Oracle, ya que parece ser una restricción de longitud clave (no creí que estuviera relacionada, hasta que la probé).

Descargar desde el sitio web de Oracle

La descarga contiene instrucciones y explica:

Debido a las restricciones de control de importación de algunos países, la versión de los archivos de políticas de JCE que se incluyen en el Java Runtime Environment o JRE (TM), el entorno 8 permite el uso de criptografía "fuerte" pero limitada. Este paquete de descarga (el que incluye este archivo README) proporciona archivos de políticas de "fuerza ilimitada" que no contienen restricciones sobre las capacidades criptográficas.

Esto aparentemente se aplica a las claves de registro también


Modificando la respuesta en base a la retroalimentación. Esta solución es probablemente una exageración pero ...

  • Le sugiero que cambie su tienda para escribir en un archivo en lugar del registro ( example )
  • Muchos productos basados ​​en Java se envían con su propia JVM. Lo hacen para que puedan ejecutarse con un archivo de políticas personalizado (que se necesitaría en su caso para escribir en una ubicación común) y ahorrar en problemas de soporte (como el uso de JVM desactualizado / no probado)

Simplemente ejecute la aplicación como administrador, o si usa eclipse, ejecute eclipse como administrador.


Vaya a su registro y cree JavaSoft/Prefs/myapp en HKEY_LOCAL_MACHINE-->SOFTWARE

Cree el nombre de la clave como Prefs y en eso cree una subclave como myapp , esto resolverá el problema.


La respuesta por Peter ya se desarrolló en el fondo, ¡pero estaba buscando una solución y la encontré!

Como no puede tocar el PlatformLogger, debe anular su mensaje:

// get rid of the bugged Preferences warning PrintStream err = System.err; System.setErr(new PrintStream(new OutputStream() { public void write(int b) {} })); Preferences PREFS = Preferences.userNodeForPackage(Settings.class); System.setErr(err);

De esta manera, la molesta advertencia desaparece sin dejar rastros. Tenga en cuenta que solo necesita hacer esto en el punto en el que hace referencia a la API de preferencias por primera vez en su programa.