use of org.eclipse.ceylon.model.typechecker.model.TypeDeclaration in project ceylon by eclipse.
the class JsonPackage method loadObject.
/**
* Loads an object declaration, creating it if necessary, and returns its type declaration.
*/
@SuppressWarnings("unchecked")
TypeDeclaration loadObject(String name, Map<String, Object> m, Scope parent, List<TypeParameter> existing) {
Value obj;
if (m.get(KEY_METATYPE) instanceof Value) {
obj = (Value) m.get(KEY_METATYPE);
} else {
obj = new Value();
m.put(KEY_METATYPE, obj);
obj.setName(name);
obj.setContainer(parent);
obj.setScope(parent);
obj.setUnit(u2);
org.eclipse.ceylon.model.typechecker.model.Class type = new org.eclipse.ceylon.model.typechecker.model.Class();
type.setName(name);
type.setAnonymous(true);
type.setUnit(u2);
type.setContainer(parent);
type.setScope(parent);
if (parent == this) {
u2.addDeclaration(obj);
u2.addDeclaration(type);
}
parent.addMember(obj);
obj.setType(type.getType());
setAnnotations(obj, (Integer) m.get(KEY_PACKED_ANNS), m.get(KEY_ANNOTATIONS));
setAnnotations(obj.getTypeDeclaration(), (Integer) m.remove(KEY_PACKED_ANNS), m.remove(KEY_ANNOTATIONS));
if (type.getExtendedType() == null) {
if (m.containsKey("super")) {
type.setExtendedType(getTypeFromJson((Map<String, Object>) m.remove("super"), parent instanceof Declaration ? (Declaration) parent : null, existing));
} else {
type.setExtendedType(getTypeFromJson(idobj, parent instanceof Declaration ? (Declaration) parent : null, existing));
}
}
if (m.containsKey(KEY_SATISFIES)) {
List<Map<String, Object>> stypes = (List<Map<String, Object>>) m.remove(KEY_SATISFIES);
type.setSatisfiedTypes(parseTypeList(stypes, existing));
}
if (m.containsKey(KEY_INTERFACES)) {
for (Map.Entry<String, Map<String, Object>> inner : ((Map<String, Map<String, Object>>) m.remove(KEY_INTERFACES)).entrySet()) {
loadInterface(inner.getKey(), inner.getValue(), type, existing);
}
}
if (m.containsKey(KEY_CLASSES)) {
for (Map.Entry<String, Map<String, Object>> inner : ((Map<String, Map<String, Object>>) m.remove(KEY_CLASSES)).entrySet()) {
loadClass(inner.getKey(), inner.getValue(), type, existing);
}
}
if (m.containsKey(KEY_OBJECTS)) {
for (Map.Entry<String, Map<String, Object>> inner : ((Map<String, Map<String, Object>>) m.remove(KEY_OBJECTS)).entrySet()) {
loadObject(inner.getKey(), inner.getValue(), type, existing);
}
}
addAttributesAndMethods(m, type, existing);
}
return obj.getTypeDeclaration();
}
use of org.eclipse.ceylon.model.typechecker.model.TypeDeclaration in project ceylon by eclipse.
the class JsonPackage method loadNestedType.
/**
* Load a nested type that hasn't been loaded yet
*/
private TypeDeclaration loadNestedType(final String fqn, List<TypeParameter> typeParams) {
try {
String[] path = fqn.split("\\.");
@SuppressWarnings("unchecked") Map<String, Object> typeMap = (Map<String, Object>) model.get(path[0]);
if (typeMap.get(KEY_METATYPE) instanceof TypeDeclaration == false) {
load(path[0], typeParams);
}
TypeDeclaration td = (TypeDeclaration) typeMap.get(KEY_METATYPE);
for (int i = 1; i < path.length; i++) {
@SuppressWarnings("unchecked") Map<String, Object> subtypes = (Map<String, Object>) typeMap.get(KEY_INTERFACES);
Map<String, Object> childMap = null;
int type = 0;
if (subtypes != null) {
childMap = (Map<String, Object>) subtypes.get(path[i]);
type = 1;
}
if (childMap == null) {
subtypes = (Map<String, Object>) typeMap.get(KEY_CLASSES);
if (subtypes != null) {
childMap = (Map<String, Object>) subtypes.get(path[i]);
type = 2;
}
}
Declaration member = td.getDirectMember(path[i], null, false);
TypeDeclaration child;
if (member instanceof Value && ((Value) member).getTypeDeclaration() instanceof Constructor)
child = ((Value) member).getTypeDeclaration().getExtendedType().getDeclaration();
else
child = (TypeDeclaration) member;
if (child == null) {
switch(type) {
case 1:
child = loadInterface(path[i], childMap, td, typeParams);
break;
case 2:
child = loadClass(path[i], childMap, td, typeParams);
break;
}
}
td = child;
}
return td;
} catch (RuntimeException x) {
throw new RuntimeException("Failed to load inner type " + fqn + " in package " + getQualifiedNameString(), x);
}
}
use of org.eclipse.ceylon.model.typechecker.model.TypeDeclaration in project ceylon by eclipse.
the class MetamodelGenerator method encodeClass.
@SuppressWarnings("unchecked")
public Map<String, Object> encodeClass(org.eclipse.ceylon.model.typechecker.model.Class d) {
final Map<String, Object> m = new HashMap<>();
m.put(KEY_METATYPE, METATYPE_CLASS);
m.put(KEY_NAME, TypeUtils.modelName(d));
// Type parameters
List<Map<String, Object>> tpl = typeParameters(d.getTypeParameters(), d);
if (tpl != null) {
m.put(KEY_TYPE_PARAMS, tpl);
}
// self type
if (d.getSelfType() != null) {
m.put(KEY_SELF_TYPE, d.getSelfType().getDeclaration().getName());
}
// Extends
if (d.getExtendedType() != null) {
m.put("super", typeMap(d.getExtendedType(), d));
}
// Satisfies
encodeTypes(d.getSatisfiedTypes(), m, KEY_SATISFIES, d);
// Initializer parameters
final List<Map<String, Object>> inits = parameterListMap(d.getParameterList(), d);
if (inits != null && !inits.isEmpty()) {
m.put(KEY_PARAMS, inits);
}
// Case types
encodeTypes(d.getCaseTypes(), m, "of", d);
// Annotations
encodeAnnotations(d.getAnnotations(), d, m);
if (d.isAnonymous()) {
m.put("$anon", 1);
}
if (d.isAlias()) {
m.put("$alias", 1);
TypeDeclaration constructor = ((ClassAlias) d).getConstructor();
if (constructor instanceof Constructor) {
m.put(KEY_CONSTRUCTOR, ((Constructor) constructor).getName());
}
// else, it's the default "constructor", and will be the (Class) d.getExtendedType().getDeclaration()
}
Map<String, Object> parent = findParent(d);
if (parent != null) {
if (parent != getPackageMap(d.getUnit().getPackage())) {
if (!parent.containsKey(KEY_CLASSES)) {
parent.put(KEY_CLASSES, new HashMap<>());
}
parent = (Map<String, Object>) parent.get(KEY_CLASSES);
}
parent.put(TypeUtils.modelName(d), m);
}
return m;
}
use of org.eclipse.ceylon.model.typechecker.model.TypeDeclaration in project ceylon by eclipse.
the class TypeUtils method qualifiedNameSkippingMethods.
/**
* Returns the qualified name of a declaration, skipping any containing methods.
*/
public static String qualifiedNameSkippingMethods(Declaration d) {
final StringBuilder p = new StringBuilder(d.getName());
Scope s = d.getContainer();
while (s != null) {
if (s instanceof org.eclipse.ceylon.model.typechecker.model.Package) {
final String pkname = ((org.eclipse.ceylon.model.typechecker.model.Package) s).getNameAsString();
if (!pkname.isEmpty()) {
p.insert(0, "::");
p.insert(0, pkname);
}
} else if (s instanceof TypeDeclaration) {
p.insert(0, '.');
p.insert(0, ((TypeDeclaration) s).getName());
}
s = s.getContainer();
}
return p.toString();
}
use of org.eclipse.ceylon.model.typechecker.model.TypeDeclaration in project ceylon by eclipse.
the class TypeUtils method metamodelTypeNameOrList.
/**
* Prints out an object with a type constructor under the property "t" and its type arguments under
* the property "a", or a union/intersection type with "u" or "i" under property "t" and the list
* of types that compose it in an array under the property "l", or a type parameter as a reference to
* already existing params.
* @param resolveTargsFromScope Indicates whether to resolve a type argument if it's within reach in the
* node's scope. This is useful for parameters of JsCallables but must be disabled for metamodel functions.
* @param node The node to use as starting point for resolution of other references.
* @param pkg The package of the current declaration
* @param pt The produced type for which a name must be output.
* @param gen The generator to use for output.
*/
static void metamodelTypeNameOrList(final boolean resolveTargsFromScope, final Node node, final org.eclipse.ceylon.model.typechecker.model.Package pkg, Type pt, SiteVariance useSiteVariance, GenerateJsVisitor gen) {
if (pt == null) {
// In dynamic blocks we sometimes get a null producedType
gen.out("'$U'");
return;
}
if (!outputMetamodelTypeList(resolveTargsFromScope, node, pkg, pt, gen)) {
TypeDeclaration type = pt.getDeclaration();
if (pt.isTypeParameter()) {
final TypeParameter tparm = (TypeParameter) type;
final Declaration tpowner = tparm.getDeclaration();
final boolean nodeIsDecl = node instanceof Tree.Declaration;
boolean rtafs = tpowner instanceof TypeDeclaration == false && (nodeIsDecl ? ((Tree.Declaration) node).getDeclarationModel() != tpowner : true);
if (rtafs && ModelUtil.contains((Scope) tpowner, node.getScope())) {
// Attempt to resolve this to an argument if the scope allows for it
if (tpowner instanceof TypeDeclaration) {
gen.out(gen.getNames().self((TypeDeclaration) tpowner), ".$$targs$$.", gen.getNames().typeParameterName(tparm));
} else if (tpowner instanceof Function) {
gen.out(gen.getNames().typeArgsParamName((Function) tpowner), ".", gen.getNames().typeParameterName(tparm));
}
} else if (resolveTargsFromScope && tpowner instanceof TypeDeclaration && (nodeIsDecl ? ((Tree.Declaration) node).getDeclarationModel() == tpowner : true) && ModelUtil.contains((Scope) tpowner, node.getScope())) {
typeNameOrList(node, tparm.getType(), gen, false);
} else {
gen.out("'", gen.getNames().typeParameterName(tparm), "'");
}
} else if (pt.isTypeAlias()) {
outputQualifiedTypename(node, gen.isImported(pkg, type), pt, gen, false);
} else {
gen.out("{t:");
// For constructors, output the type of the class
final Type qt = type instanceof Constructor ? pt.getQualifyingType() : pt;
outputQualifiedTypename(node, gen.isImported(pkg, type), qt, gen, false);
// Type Parameters
if (!pt.getTypeArguments().isEmpty()) {
gen.out(",a:{");
boolean first = true;
for (Map.Entry<TypeParameter, Type> e : pt.getTypeArguments().entrySet()) {
if (first)
first = false;
else
gen.out(",");
gen.out(gen.getNames().typeParameterName(e.getKey()), ":");
metamodelTypeNameOrList(resolveTargsFromScope, node, pkg, e.getValue(), pt.getVarianceOverrides().get(e.getKey()), gen);
}
gen.out("}");
}
printSiteVariance(useSiteVariance, gen);
gen.out("}");
}
}
}
Aggregations