JDK-6613858 : ObjectName Constructor declaration breaks Properties() argument in 1.6
  • Type: Bug
  • Component: core-svc
  • Sub-Component: javax.management
  • Affected Version: 6
  • Priority: P3
  • Status: Closed
  • Resolution: Won't Fix
  • OS: linux
  • CPU: x86
  • Submitted: 2007-10-06
  • Updated: 2010-07-29
  • Resolved: 2007-10-08
Related Reports
Relates :  
Relates :  
Description
FULL PRODUCT VERSION :
# java -version
java version "1.5.0_12"
Java(TM) 2 Runtime Environment, Standard Edition (build 1.5.0_12-b04)
Java HotSpot(TM) Client VM (build 1.5.0_12-b04, mixed mode, sharing)

ADDITIONAL OS VERSION INFORMATION :
# uname -a
Linux dev199.shsolutions.com 2.6.18-1.2798.fc6 #1 SMP Mon Oct 16 14:37:32 EDT 2006 i686 i686 i386 GNU/Linux


A DESCRIPTION OF THE PROBLEM :


B/c the constructor definition for ObjectName changed from 1.5 to 1.6

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
import java.util.Hashtable;
import java.util.Properties;

import javax.management.ObjectName;
import javax.management.MalformedObjectNameException;


/**
 * Hello world!
 *
 */
public class App
{
	public String value = "hi";
	public ObjectName objectName;
	public Hashtable<String,String> props;
	public Properties properties;

	public App() {
	}

    public static void main( String[] args ) throws MalformedObjectNameException
    {
		App app = new App();
		
		app.props = new Hashtable<String,String>();
		app.props.put("11","22");

		app.properties = new Properties();
	
		app.properties.setProperty("1","a");
		app.properties.setProperty("2","b");

	    app.objectName = new ObjectName("string name", app.properties);
        System.out.println( "Hello World!  : " + app.value );
        System.out.println( "ObjectName is : " + app.objectName );
    }
}


EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
Hello World!  : hi
ObjectName is : string name:2=b,1=a
ACTUAL -
Cannot even compile....



ERROR MESSAGES/STACK TRACES THAT OCCUR :
[INFO] Compilation failure
App.java:[36,22] cannot find symbol
symbol  : constructor ObjectName(java.lang.String,java.util.Properties)
location: class javax.management.ObjectName


REPRODUCIBILITY :
This bug can be reproduced always.

---------- BEGIN SOURCE ----------
import java.util.Hashtable;
import java.util.Properties;

import javax.management.ObjectName;
import javax.management.MalformedObjectNameException;


/**
 * Hello world!
 *
 */
public class App
{
	public String value = "hi";
	public ObjectName objectName;
	public Hashtable<String,String> props;
	public Properties properties;

	public App() {
	}

    public static void main( String[] args ) throws MalformedObjectNameException
    {
		App app = new App();
		
		app.props = new Hashtable<String,String>();
		app.props.put("11","22");

		app.properties = new Properties();
	
		app.properties.setProperty("1","a");
		app.properties.setProperty("2","b");

             //  The line below compiles in 1.5 but not in 1.6
	    app.objectName = new ObjectName("string name", app.properties);
        System.out.println( "Hello World!  : " + app.value );
        System.out.println( "ObjectName is : " + app.objectName );
    }
}

---------- END SOURCE ----------

CUSTOMER SUBMITTED WORKAROUND :
no work around

Release Regression From : 5.0u12
The above release value was the last known release where this 
bug was not reproducible. Since then there has been a regression.

Release Regression From : 5.0u12
The above release value was the last known release where this 
bug was not reproducible. Since then there has been a regression.

Comments
EVALUATION This is a known problem. The root cause is that Properties extends Hashtable<Object,Object> where we might expect it to extend Hashtable<String,String>. That in turn is because nothing stopped you in the past from using the inherited Hashtable methods to put a non-String into a Properties. See the referenced bugs for further details. We could change the signature of the ObjectName constructor to accept Hashtable<?,?> instead of Hashtable<String,String> so that it would accept a Properties, but I think that would be a pity. The Hashtable in question really does have to have Strings as its keys and values. The fact that a Properties is not accepted today serves as a reminder that you have to check that the Properties really does contain only Strings. We could also add a new ObjectName constructor that takes a Properties argument, but that would be a signature change, which means that it could only happen in the Java SE 7 platform. Existing code that uses Properties will have failed to compile on Java SE 6 in the meantime, so fixing it in Java SE 7 is too late. Code that used Properties presumably did so because, before generics, it was a convenient way to get an object that was effectively a Hashtable<String,String>. New code should just use a Hashtable<String,String> directly.
08-10-2007