I decided to go hog wild and clean up all the type use in Presents which
required some serious bending and folding of the generic type system, but for the most part we managed to avoid any mutilating. The gendobj task now generates properly typed "addToXXX" and "updateXXX" DSet methods based on the parameterized type of the DSet. This might cause unrecompiled code to break, but I don't think there are many cases in the base toolkit where people call DSet adders or updaters. We'll see and I'll add backwards compatibility versions for cases where we need them to support GG games (everything else we can just recompile). git-svn-id: svn+ssh://src.earth.threerings.net/narya/trunk@4245 542714f4-19e9-0310-aa3c-eee0fc999fb1
This commit is contained in:
@@ -31,6 +31,8 @@ import java.io.StringWriter;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.Modifier;
|
||||
import java.lang.reflect.ParameterizedType;
|
||||
import java.lang.reflect.Type;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
@@ -109,9 +111,7 @@ public class GenDObjectTask extends Task
|
||||
throw new BuildException("Can't resolve InvocationListener", e);
|
||||
}
|
||||
|
||||
ArrayList files = new ArrayList();
|
||||
for (Iterator iter = _filesets.iterator(); iter.hasNext(); ) {
|
||||
FileSet fs = (FileSet)iter.next();
|
||||
for (FileSet fs : _filesets) {
|
||||
DirectoryScanner ds = fs.getDirectoryScanner(getProject());
|
||||
File fromDir = fs.getDir(getProject());
|
||||
String[] srcFiles = ds.getIncludedFiles();
|
||||
@@ -158,7 +158,7 @@ public class GenDObjectTask extends Task
|
||||
}
|
||||
|
||||
// determine which fields we need to deal with
|
||||
ArrayList flist = new ArrayList();
|
||||
ArrayList<Field> flist = new ArrayList<Field>();
|
||||
Field[] fields = oclass.getDeclaredFields();
|
||||
for (int ii = 0; ii < fields.length; ii++) {
|
||||
Field f = fields[ii];
|
||||
@@ -175,12 +175,12 @@ public class GenDObjectTask extends Task
|
||||
String[] lines = null;
|
||||
try {
|
||||
BufferedReader bin = new BufferedReader(new FileReader(source));
|
||||
ArrayList llist = new ArrayList();
|
||||
ArrayList<String> llist = new ArrayList<String>();
|
||||
String line = null;
|
||||
while ((line = bin.readLine()) != null) {
|
||||
llist.add(line);
|
||||
}
|
||||
lines = (String[])llist.toArray(new String[llist.size()]);
|
||||
lines = llist.toArray(new String[llist.size()]);
|
||||
bin.close();
|
||||
} catch (IOException ioe) {
|
||||
System.err.println("Error reading '" + source + "': " + ioe);
|
||||
@@ -249,8 +249,8 @@ public class GenDObjectTask extends Task
|
||||
StringBuilder fsection = new StringBuilder();
|
||||
StringBuilder msection = new StringBuilder();
|
||||
for (int ii = 0; ii < flist.size(); ii++) {
|
||||
Field f = (Field)flist.get(ii);
|
||||
Class ftype = f.getType();
|
||||
Field f = flist.get(ii);
|
||||
Class<?> ftype = f.getType();
|
||||
String fname = f.getName();
|
||||
|
||||
// create our velocity context
|
||||
@@ -262,13 +262,34 @@ public class GenDObjectTask extends Task
|
||||
ctx.put("clonefield", GenUtil.cloneArgument(_dsclass, f, "value"));
|
||||
ctx.put("capfield", StringUtil.unStudlyName(fname).toUpperCase());
|
||||
ctx.put("upfield", StringUtils.capitalize(fname));
|
||||
|
||||
// if this field is an array, we need its component types
|
||||
if (ftype.isArray()) {
|
||||
Class etype = ftype.getComponentType();
|
||||
Class<?> etype = ftype.getComponentType();
|
||||
ctx.put("elemtype", GenUtil.simpleName(etype));
|
||||
ctx.put("wrapelem", GenUtil.boxArgument(etype, "value"));
|
||||
ctx.put("wrapoelem", GenUtil.boxArgument(etype, "ovalue"));
|
||||
}
|
||||
|
||||
// if this field is a generic DSet, we need its bound type
|
||||
if (_dsclass.isAssignableFrom(ftype)) {
|
||||
Type t = f.getGenericType();
|
||||
// we need to walk up the heirarchy until we get to the
|
||||
// parameterized DSet
|
||||
while (t instanceof Class<?>) {
|
||||
t = ((Class<?>)t).getGenericSuperclass();
|
||||
}
|
||||
if (t instanceof ParameterizedType) {
|
||||
ParameterizedType pt = (ParameterizedType)t;
|
||||
if (pt.getActualTypeArguments().length > 0) {
|
||||
ctx.put("etype", GenUtil.simpleName(
|
||||
(Class<?>)pt.getActualTypeArguments()[0]));
|
||||
}
|
||||
} else {
|
||||
ctx.put("etype", "DSet.Entry");
|
||||
}
|
||||
}
|
||||
|
||||
// now figure out which template to use
|
||||
String tname = "field.tmpl";
|
||||
if (_dsclass.isAssignableFrom(ftype)) {
|
||||
@@ -370,7 +391,7 @@ public class GenDObjectTask extends Task
|
||||
}
|
||||
|
||||
/** A list of filesets that contain tile images. */
|
||||
protected ArrayList _filesets = new ArrayList();
|
||||
protected ArrayList<FileSet> _filesets = new ArrayList<FileSet>();
|
||||
|
||||
/** Used to do our own classpath business. */
|
||||
protected ClassLoader _cloader;
|
||||
@@ -380,15 +401,15 @@ public class GenDObjectTask extends Task
|
||||
|
||||
/** {@link DObject} resolved with the proper classloader so that we
|
||||
* can compare it to loaded derived classes. */
|
||||
protected Class _doclass;
|
||||
protected Class<?> _doclass;
|
||||
|
||||
/** {@link DSet} resolved with the proper classloader so that we can
|
||||
* compare it to loaded derived classes. */
|
||||
protected Class _dsclass;
|
||||
protected Class<?> _dsclass;
|
||||
|
||||
/** {@link OidList} resolved with the proper classloader so that we
|
||||
* can compare it to loaded derived classes. */
|
||||
protected Class _olclass;
|
||||
protected Class<?> _olclass;
|
||||
|
||||
/** Specifies the start of the path to our various templates. */
|
||||
protected static final String BASE_TMPL =
|
||||
|
||||
@@ -68,8 +68,9 @@ public class GenReceiverTask extends InvocationTask
|
||||
return;
|
||||
}
|
||||
|
||||
HashMap imports = new HashMap();
|
||||
ComparableArrayList methods = new ComparableArrayList();
|
||||
HashMap<String,Boolean> imports = new HashMap<String,Boolean>();
|
||||
ComparableArrayList<ServiceMethod> methods =
|
||||
new ComparableArrayList<ServiceMethod>();
|
||||
|
||||
// we need to import the receiver itself
|
||||
imports.put(importify(receiver.getName()), Boolean.TRUE);
|
||||
@@ -94,14 +95,14 @@ public class GenReceiverTask extends InvocationTask
|
||||
}
|
||||
|
||||
protected void generateSender (File source, String rname, String rpackage,
|
||||
List methods, Iterator imports)
|
||||
List methods, Iterator<String> imports)
|
||||
{
|
||||
String name = StringUtil.replace(rname, "Receiver", "");
|
||||
String sname = StringUtil.replace(rname, "Receiver", "Sender");
|
||||
String spackage = StringUtil.replace(rpackage, ".client", ".server");
|
||||
|
||||
// construct our imports list
|
||||
ComparableArrayList implist = new ComparableArrayList();
|
||||
ComparableArrayList<String> implist = new ComparableArrayList<String>();
|
||||
CollectionUtil.addAll(implist, imports);
|
||||
checkedAdd(implist, ClientObject.class.getName());
|
||||
checkedAdd(implist, InvocationSender.class.getName());
|
||||
@@ -134,13 +135,13 @@ public class GenReceiverTask extends InvocationTask
|
||||
|
||||
protected void generateDecoder (
|
||||
File source, String rname, String rpackage, List methods,
|
||||
Iterator imports)
|
||||
Iterator<String> imports)
|
||||
{
|
||||
String name = StringUtil.replace(rname, "Receiver", "");
|
||||
String dname = StringUtil.replace(rname, "Receiver", "Decoder");
|
||||
|
||||
// construct our imports list
|
||||
ComparableArrayList implist = new ComparableArrayList();
|
||||
ComparableArrayList<String> implist = new ComparableArrayList<String>();
|
||||
CollectionUtil.addAll(implist, imports);
|
||||
checkedAdd(implist, InvocationDecoder.class.getName());
|
||||
implist.sort();
|
||||
|
||||
@@ -37,13 +37,15 @@ import com.threerings.presents.server.InvocationProvider;
|
||||
public class GenServiceTask extends InvocationTask
|
||||
{
|
||||
/** Used to keep track of custom InvocationListener derivations. */
|
||||
public class ServiceListener implements Comparable
|
||||
public class ServiceListener implements Comparable<ServiceListener>
|
||||
{
|
||||
public Class listener;
|
||||
|
||||
public ComparableArrayList methods = new ComparableArrayList();
|
||||
public ComparableArrayList<ServiceMethod> methods =
|
||||
new ComparableArrayList<ServiceMethod>();
|
||||
|
||||
public ServiceListener (Class service, Class listener, HashMap imports)
|
||||
public ServiceListener (Class service, Class listener,
|
||||
HashMap<String,Boolean> imports)
|
||||
{
|
||||
this.listener = listener;
|
||||
Method[] methdecls = listener.getDeclaredMethods();
|
||||
@@ -59,9 +61,9 @@ public class GenServiceTask extends InvocationTask
|
||||
methods.sort();
|
||||
}
|
||||
|
||||
public int compareTo (Object other)
|
||||
public int compareTo (ServiceListener other)
|
||||
{
|
||||
return getName().compareTo(((ServiceListener)other).getName());
|
||||
return getName().compareTo(other.getName());
|
||||
}
|
||||
|
||||
public boolean equals (Object other)
|
||||
@@ -115,9 +117,11 @@ public class GenServiceTask extends InvocationTask
|
||||
return;
|
||||
}
|
||||
|
||||
HashMap imports = new HashMap();
|
||||
ComparableArrayList methods = new ComparableArrayList();
|
||||
ComparableArrayList listeners = new ComparableArrayList();
|
||||
HashMap<String,Boolean> imports = new HashMap<String,Boolean>();
|
||||
ComparableArrayList<ServiceMethod> methods =
|
||||
new ComparableArrayList<ServiceMethod>();
|
||||
ComparableArrayList<ServiceListener> listeners =
|
||||
new ComparableArrayList<ServiceListener>();
|
||||
|
||||
// we need to import the service itself
|
||||
imports.put(importify(service.getName()), Boolean.TRUE);
|
||||
@@ -158,14 +162,14 @@ public class GenServiceTask extends InvocationTask
|
||||
|
||||
protected void generateMarshaller (
|
||||
File source, String sname, String spackage, List methods,
|
||||
List listeners, Iterator imports)
|
||||
List listeners, Iterator<String> imports)
|
||||
{
|
||||
String name = StringUtil.replace(sname, "Service", "");
|
||||
String mname = StringUtil.replace(sname, "Service", "Marshaller");
|
||||
String mpackage = StringUtil.replace(spackage, ".client", ".data");
|
||||
|
||||
// construct our imports list
|
||||
ComparableArrayList implist = new ComparableArrayList();
|
||||
ComparableArrayList<String> implist = new ComparableArrayList<String>();
|
||||
CollectionUtil.addAll(implist, imports);
|
||||
checkedAdd(implist, Client.class.getName());
|
||||
checkedAdd(implist, InvocationMarshaller.class.getName());
|
||||
@@ -198,14 +202,14 @@ public class GenServiceTask extends InvocationTask
|
||||
|
||||
protected void generateDispatcher (
|
||||
File source, String sname, String spackage, List methods,
|
||||
Iterator imports)
|
||||
Iterator<String> imports)
|
||||
{
|
||||
String name = StringUtil.replace(sname, "Service", "");
|
||||
String dname = StringUtil.replace(sname, "Service", "Dispatcher");
|
||||
String dpackage = StringUtil.replace(spackage, ".client", ".server");
|
||||
|
||||
// construct our imports list
|
||||
ComparableArrayList implist = new ComparableArrayList();
|
||||
ComparableArrayList<String> implist = new ComparableArrayList<String>();
|
||||
CollectionUtil.addAll(implist, imports);
|
||||
checkedAdd(implist, ClientObject.class.getName());
|
||||
checkedAdd(implist, InvocationMarshaller.class.getName());
|
||||
@@ -241,14 +245,14 @@ public class GenServiceTask extends InvocationTask
|
||||
|
||||
protected void generateProvider (
|
||||
File source, String sname, String spackage, List methods,
|
||||
List listeners, Iterator imports)
|
||||
List listeners, Iterator<String> imports)
|
||||
{
|
||||
String name = StringUtil.replace(sname, "Service", "");
|
||||
String mname = StringUtil.replace(sname, "Service", "Provider");
|
||||
String mpackage = StringUtil.replace(spackage, ".client", ".server");
|
||||
|
||||
// construct our imports list
|
||||
ComparableArrayList implist = new ComparableArrayList();
|
||||
ComparableArrayList<String> implist = new ComparableArrayList<String>();
|
||||
CollectionUtil.addAll(implist, imports);
|
||||
checkedAdd(implist, ClientObject.class.getName());
|
||||
checkedAdd(implist, InvocationProvider.class.getName());
|
||||
@@ -280,7 +284,7 @@ public class GenServiceTask extends InvocationTask
|
||||
}
|
||||
|
||||
/** Services for which we should not generate provider interfaces. */
|
||||
protected HashSet _providerless = new HashSet();
|
||||
protected HashSet<String> _providerless = new HashSet<String>();
|
||||
|
||||
/** Specifies the path to the marshaller template. */
|
||||
protected static final String MARSHALLER_TMPL =
|
||||
|
||||
@@ -46,7 +46,7 @@ public abstract class InvocationTask extends Task
|
||||
|
||||
public Class listener;
|
||||
|
||||
public ListenerArgument (int index, Class listener)
|
||||
public ListenerArgument (int index, Class<?> listener)
|
||||
{
|
||||
this.index = index+1;
|
||||
this.listener = listener;
|
||||
@@ -65,21 +65,23 @@ public abstract class InvocationTask extends Task
|
||||
}
|
||||
|
||||
/** Used to keep track of invocation service methods. */
|
||||
public class ServiceMethod implements Comparable
|
||||
public class ServiceMethod implements Comparable<ServiceMethod>
|
||||
{
|
||||
public Method method;
|
||||
|
||||
public ArrayList listenerArgs = new ArrayList();
|
||||
public ArrayList<ListenerArgument> listenerArgs =
|
||||
new ArrayList<ListenerArgument>();
|
||||
|
||||
public ServiceMethod (Class service, Method method, HashMap imports)
|
||||
public ServiceMethod (Class<?> service, Method method,
|
||||
HashMap<String,Boolean> imports)
|
||||
{
|
||||
this.method = method;
|
||||
|
||||
// we need to look through our arguments and note any needed
|
||||
// imports in the supplied table
|
||||
Class[] args = method.getParameterTypes();
|
||||
Class<?>[] args = method.getParameterTypes();
|
||||
for (int ii = 0; ii < args.length; ii++) {
|
||||
Class arg = args[ii];
|
||||
Class<?> arg = args[ii];
|
||||
while (arg.isArray()) {
|
||||
arg = arg.getComponentType();
|
||||
}
|
||||
@@ -132,7 +134,7 @@ public abstract class InvocationTask extends Task
|
||||
public String getArgList (boolean skipFirst)
|
||||
{
|
||||
StringBuilder buf = new StringBuilder();
|
||||
Class[] args = method.getParameterTypes();
|
||||
Class<?>[] args = method.getParameterTypes();
|
||||
for (int ii = skipFirst ? 1 : 0; ii < args.length; ii++) {
|
||||
if (buf.length() > 0) {
|
||||
buf.append(", ");
|
||||
@@ -146,7 +148,7 @@ public abstract class InvocationTask extends Task
|
||||
public String getWrappedArgList (boolean skipFirst)
|
||||
{
|
||||
StringBuilder buf = new StringBuilder();
|
||||
Class[] args = method.getParameterTypes();
|
||||
Class<?>[] args = method.getParameterTypes();
|
||||
for (int ii = (skipFirst ? 1 : 0); ii < args.length; ii++) {
|
||||
if (buf.length() > 0) {
|
||||
buf.append(", ");
|
||||
@@ -161,15 +163,15 @@ public abstract class InvocationTask extends Task
|
||||
return (method.getParameterTypes().length > (skipFirst ? 1 : 0));
|
||||
}
|
||||
|
||||
public int compareTo (Object other)
|
||||
public int compareTo (ServiceMethod other)
|
||||
{
|
||||
return getCode().compareTo(((ServiceMethod)other).getCode());
|
||||
return getCode().compareTo(other.getCode());
|
||||
}
|
||||
|
||||
public String getUnwrappedArgList (boolean listenerMode)
|
||||
{
|
||||
StringBuilder buf = new StringBuilder();
|
||||
Class[] args = method.getParameterTypes();
|
||||
Class<?>[] args = method.getParameterTypes();
|
||||
for (int ii = (listenerMode ? 0 : 1); ii < args.length; ii++) {
|
||||
if (buf.length() > 0) {
|
||||
buf.append(", ");
|
||||
@@ -180,7 +182,7 @@ public abstract class InvocationTask extends Task
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
protected String boxArgument (Class clazz, int index)
|
||||
protected String boxArgument (Class<?> clazz, int index)
|
||||
{
|
||||
if (_ilistener.isAssignableFrom(clazz)) {
|
||||
return GenUtil.boxArgument(clazz, "listener" + index);
|
||||
@@ -190,7 +192,7 @@ public abstract class InvocationTask extends Task
|
||||
}
|
||||
|
||||
protected String unboxArgument (
|
||||
Class clazz, int index, boolean listenerMode)
|
||||
Class<?> clazz, int index, boolean listenerMode)
|
||||
{
|
||||
if (listenerMode && _ilistener.isAssignableFrom(clazz)) {
|
||||
return "listener" + index;
|
||||
@@ -252,8 +254,7 @@ public abstract class InvocationTask extends Task
|
||||
throw new BuildException("Can't resolve InvocationListener", e);
|
||||
}
|
||||
|
||||
for (Iterator iter = _filesets.iterator(); iter.hasNext(); ) {
|
||||
FileSet fs = (FileSet)iter.next();
|
||||
for (FileSet fs : _filesets) {
|
||||
DirectoryScanner ds = fs.getDirectoryScanner(getProject());
|
||||
File fromDir = fs.getDir(getProject());
|
||||
String[] srcFiles = ds.getIncludedFiles();
|
||||
@@ -302,7 +303,7 @@ public abstract class InvocationTask extends Task
|
||||
FileUtils.writeStringToFile(new File(path), data, "UTF-8");
|
||||
}
|
||||
|
||||
protected static void checkedAdd (List list, Object value)
|
||||
protected static <T> void checkedAdd (List<T> list, T value)
|
||||
{
|
||||
if (!list.contains(value)) {
|
||||
list.add(value);
|
||||
@@ -324,7 +325,7 @@ public abstract class InvocationTask extends Task
|
||||
}
|
||||
|
||||
/** A list of filesets that contain tile images. */
|
||||
protected ArrayList _filesets = new ArrayList();
|
||||
protected ArrayList<FileSet> _filesets = new ArrayList<FileSet>();
|
||||
|
||||
/** A header to put on all generated source files. */
|
||||
protected String _header;
|
||||
@@ -337,5 +338,5 @@ public abstract class InvocationTask extends Task
|
||||
|
||||
/** {@link InvocationListener} resolved with the proper classloader so
|
||||
* that we can compare it to loaded derived classes. */
|
||||
protected Class _ilistener;
|
||||
protected Class<?> _ilistener;
|
||||
}
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
* <code>$field</code> set. The set will not change until the event is
|
||||
* actually propagated through the system.
|
||||
*/
|
||||
public void addTo$upfield (DSet.Entry elem)
|
||||
public void addTo$upfield ($etype elem)
|
||||
{
|
||||
requestEntryAdd($capfield, $field, elem);
|
||||
}
|
||||
@@ -23,7 +23,7 @@
|
||||
* <code>$field</code> set. The set will not change until the event is
|
||||
* actually propagated through the system.
|
||||
*/
|
||||
public void update$upfield (DSet.Entry elem)
|
||||
public void update$upfield ($etype elem)
|
||||
{
|
||||
requestEntryUpdate($capfield, $field, elem);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user