Use Constants interface in GWT Project - java

I have not yet used Constants interface in GWT and I am having problem to run the example CellTable. The deferred binding fails and the central error message is: "No resource found for contactDataBaseCategories". contactDataBaseCategories is a method defined in the interface DataBaseConstants and returns an array of Strings. I suspect I must create a properties (txt?) file and to define the categories, but I am not sure, since I come across this case for the first time. How can I do it properly to make the example of the CellTable run?
Update: I have created the ContactDatabase.DatabaseConstants.properties file in the same package in which the interface is declared, I have added the line in the file:
contactDataBaseCategories = friends, coWorkers, other
but it still does not work. The error is again : "No resource found for contactDataBaseCategories" and then
"Deferred Binding failed for com.al.celltablöeexample.ContactDatabase.DatabaseConstants".
What going wrong?

This is how i do it
Constant interface
public interface DataBaseConstants extends Constants
{
#Key("contact-database-categories")
String contactDataBaseCategories();
}
property file. DataBaseConstants.properties
contact-database-categories = "Your String"
You can use it
public DataBaseConstants dbConstant= GWT.create( DataBaseConstants .class );
dbConstant.contactDataBaseCategories();
Edited
If you want to pass string array then you can do it like this
#DefaultStringArrayValue({"cat1", "cat2", "cat3", "cat4", "cat5"})
String[] contactDataBaseCategories();
More about Constants

I have finally managed it. The problem was that it could not find the resource/file: ContactDatabase.DatabaseConstants.properties. I have changed it to DatabaseConstants.properties and I removed the inner interface to its own file. The same I did in the class CwCellTable on the interface CwConstants. In the example page moreover, the instantiation of the CwConstants interface is missed, and one must do also this (in the constructor), like in the ContactDatabase class.

Just to add to Dilantha's answer you can then set
contact-database-categories = Family, Friends, Coworkers, Businesses, Contacts
in order to comply with the example.
Tip : In order to make the example work create a costructor in CwCellList and add the following :
initWidget(onInitialize());

Related

system classloader does not use the overriden method

I have a program that generates classes using JCodemodel and a dynamic class loader. I parse a yaml file, generate the required classes and map the structure of the file . Everything is fine so far.
Snakeyaml handles the parse and write nicely, so the definition of classes if fine.
Then I try to access a method properties() which is redefined in the yaml.
I first load the file into a "Tree", load its root element as a "Compute" and print its class and methods ; then I call the overridden method.
The computeb class is dynamicaly generated, as well as the computeb$Properties.
here is the code (I replaced my packages by shorter ones):
Tree tree = Parser.load(new FileInputStream("src/test/resources/tree.yaml"));
mypackage.Compute c = (mypackage.Compute) tree.root();
System.err.println("class : " + c.getClass());
for (Method m : c.getClass().getMethods()) {
System.err.println(" method : " + m);
}
System.err.println("properties() class is " + c.properties().getClass().getName());
The result is :
class : class computeb
method : public computeb$Property computeb.properties()
method : public mypackage.Compute$Property mypackage.Compute.properties()
(...)
properties() class is mypackage.Compute$Property
As you notice, the class has the two methods present, however the properties() method called is the second one. I would want to call the first one (which is defined in the classloader) . Why does it happen this way ? What should I do ?
OK I got it, I had an issue while statically generating the classes on a specific folder.
Since I had to resolve existing classes to avoid creating them twice, I only resolved classes that were starting with my package prefix.
This worked well in static generation, but in dynamic generation I had previously generated classes I could not load, while they already were present. Basically that means that my class generator was creating another class with same name, so sometimes the classloader could refer to one class, sometimes to another.
I'm working on correcting this dirty mess.

How to resolve file name issue with multiple interfaces names, created in a file

how to :
when i create multiple interface(s) to check details, I have learn that of multiple extension of interface with interfaces.
it gives me error with file name , because previous I was named the file with interface name ,primarily developed but when i make new interface(s) ,editor frequently told me to rename the file name with currently developed interface .
what is the conflict & how to resolve .
Each public type has to be in its own file. For example, if you have class declared like this:
public class MyClass {...}
You have to put it in a file called MyClass.java.
An interface is also considered a type in Java. Therefore, if you have an interface such as:
public interface MyInterface {....}
You also have to put it in its own file named like the name of the interface, that is, MyInterface.java.
The same is also true of enum. If it's public enum, it goes in its own file named like the enum.
If you have non-public types, you can put them in the same file as another type. But as soon as you make them public, you need to move them to their own file.

How to invoke methods of a class (in java) when class name and method name are stored in two different strings

Well, not sure if the question sounds a little weird but let me try to put forth the clarification :
I have a JSP page. On this JSP page, I am calling a java class defined in one of my packages under my projects. This class connects to database and access a table which has got fields namely - functionname, function class. Now I am able to retrieve in my JSP the two strings, lets say -
String funName = "ComFunctions";
String className = "funLog");
Now, I want to invoke this function using this class name i.e. basically something like - className.funName
Is it possible in Java? Actually, these functions and class names will be retrieved in a for loop, so I can't directly call using real classname but have to use strings.
Kindly suggest if there is a way or worl around or if the question is still unclear.
I tried the following approach so far but no luck -
Class c = Class.forName(className);
Object o = c.newInstance();
Method m = c.getMethod(funName, String.class); // Not sure what is supposed to be second parameter here i.e. after funName
Error - the above code gives " No class found error". And i made sure that class is there under the package. Even adding package name i.e. packge.classname didnt help and it says "Symbol not found" for package name.
Any pointers please?
Example class that I am trying to invoke -
package mypackage;
public class ComFunctions extends WDriverInitialize{
public static void main(String[] args){
}
public static void funLog(String username){
System.out.println(userName);
}
}
You need to make sure the compiled class is in the webapp's classpath (ie, WEB-INF/classes) and use the FQN (ie, add the package name). You could also make a JAR file of your classes and add that to the WEB-INF/lib folder.
Also, the extra parameter in getMethod is to fetch a method with the matching parameters (ie, in your example, one that takes a String
You're missing one piece of the puzzle, and that's the method arguments. Without it, you can't really be sure what method funName is referring to, and what arguments to pass to it.
And of course, the class needs to be in the classpath.

Configuration class - best practice with Guice

Background: I'm using Google Guice and so it's easier to pass through the configuration class but I think this is not the best way.
I have a configuration class which stores some paths:
class Configuration{
String getHomePath();
String getUserPath();
}
Also I have a class "a" which needs the "homepath" and a class "b" which needs the "userpath".
Is it better to pass the configuration class through the constructor of class a and b or only pass through the specific path?
If you're really using Guice correctly all your configuration like this should appear in modules' configure method. So:
Remove the configuration class.
Create annotation classes, probably called HomePath and UserPath.
Where class a uses getHomePath() replace that with a String field member named homePath.
Where class b uses getUserPath() replace that with a String field member named userPath.
Modify the class a and b constructors to be #Inject annotated (should already be) and take in a String parameter, respectively annotated with #HomePath and #UserPath and assign the String field member that injected value.
Create bindings in your module's configure method use .annotatedWith() which define correct values; if they're only available at run time, bind a provider.
E.G.
class a {
private String homePath;
#Inject
public a(#HomePath String homePath) {
this.homePath = homePath;
}
public String tellMeAboutHome() {
return "We live in a nice home called " + homePath;
}
}
class customModule extends AbstractModule {
public static final String userPath = "/home/rafael";
public void configure() {
bind(String.class).annotatedWith(HomePath.class).to("/home/");
bind(String.class).annotatedWith(UserPath.class).to(userPath);
}
}
If creating annotations is too much work for you, use the #Named annotation Guice ships with.
There's no single answer to your question, there are only options to choose from, based on your specific situation.
If you know your Configuration class is going to grow AND if it's likely for your A and B classes will use more from it, then pass the whole Configuration object to their constructors. NB: I know this is against the YAGNI principle but sometimes you may know you're gonna need it ;-)
Otherwise, you can consider using #Named injection of your paths so that you reduce A and B classes dependencies to their minimum, which is a good design practice.
The general rule is code to make the dependency graph (which classes know about or depend on other classes/ interfaces) as simple, regular and fixed as possible.
If not passing the Configuration class makes a or b have zero dependencies on on user-written classes, or is necessary to avoid a dependency loop, then use the individual path strings. Otherwise, if it makes more sense to say 'this class has access to configuration info, in a way that may change in the future', pass the class.
I'd avoid the singleton approach, especially if you already have Guice set up.

Automatic factory registration

i'm just learning java, and i meet some problems.
Here we have simple factory pattern:
public class SomeFactory {
...
public static void registerProduct(String name, Class<? extends IProduct > f)
}
public SomeProduct implements IProduct {
static {
SomeFactory.register("some product", SomeProduct.class);
}
...
}
All products should register themselves at factory.
But before using this code, all Products classes should be loaded.
I can put Class.forName() somewhere, for example in main function.
But i want to avoid such sort of manual classes loading. I want just add new IProduct
implementations, without updating other parts(such as SomeFactory or Main methods, etc.).
But i wonder, is it possible to automatically load some classes(marked with annotation, for example)?
P.S I want to notice, that no other classes will be added at run-time, all IProduct implementations are known before compiling.
UPD#1
Thank for your answering!
But is it possible to make auto-generated property-file with IProduct instances?
I mean is it possible to make some build-time script(for maven for example) that generates property-file or loader code? Are there such solutions or frameworks?
UPD#2
I finished with using Reflections library that provides run-time information, by scanning classpath at startup.
This is possible, but not easily. It would need to scan all the classes in the classpath to see if they have an annotation or implement the IProduct interface. See How do you find all subclasses of a given class in Java? for answers to such a problem.
I would do keep it simple and just have a list of classes to load, either in the factory itself, or in an external file (properties file, for example).
Have each product register itself, using a static block like this:
class MyProduct1{
static{
SomeFactory.register(MyProduct1.getClass());
}
..
..
}
An external property file can keep track of all Products.
Your main method can parse this list of Products and do a Class.forName("..").
This way you wouldnt need to code any specific product, just the property file keeps changing. Ah! yes adding security registration would also be a plus point.
Note: I'm just proposing an idea, I'vent tried it myself :)

Categories

Resources