SpecifiedArgument.ceylon
import ceylon.ast.core {
Node,
SpecifiedArgument,
ValueSpecification,
LazySpecifier,
FunctionArgument,
LazySpecification,
ValueArgument
}
import com.redhat.ceylon.compiler.typechecker.tree {
JNode=Node,
Tree {
JFunctionModifier=FunctionModifier,
JNamedArgument=NamedArgument,
JSpecifiedArgument=SpecifiedArgument,
JTypedArgument=TypedArgument,
JValueModifier=ValueModifier
}
}
"""Converts a RedHat AST [[NamedArgument|JNamedArgument]] to a `ceylon.ast` [[SpecifiedArgument]].
The main RedHat AST type for specified arguments is [[SpecifiedArgument|JSpecifiedArgument]];
however, lazy specifications like
val => "Hello, World!";
comparing(Integer x, Integer y) => x.magnitude <=> y.magnitude;
are instead parsed as [[AttributeArguments|Tree.AttributeArgument]] / [[FunctionArguments|Tree.FunctionArgument]]
with a synthetic ‘`function`’ / ‘`value`’ modifier (`null` token)."""
shared SpecifiedArgument specifiedArgumentToCeylon(JNamedArgument specifiedArgument, Anything(JNode,Node) update = noop) {
SpecifiedArgument result;
if (is JSpecifiedArgument specifiedArgument) {
value valueSpecification = ValueSpecification(lIdentifierToCeylon(specifiedArgument.identifier, update), specifierToCeylon(specifiedArgument.specifierExpression, update));
update(specifiedArgument, valueSpecification);
result = SpecifiedArgument(valueSpecification);
} else {
assert (is JTypedArgument specifiedArgument, exists type = specifiedArgument.type, !type.mainToken exists);
if (type is JFunctionModifier) {
assert (is FunctionArgument functionArgument = inlineDefinitionArgumentToCeylon(specifiedArgument, update));
assert (is LazySpecifier definition = functionArgument.definition);
value lazySpecification = LazySpecification {
name = functionArgument.name;
parameterLists = functionArgument.parameterLists;
specifier = definition;
};
update(specifiedArgument, lazySpecification);
result = SpecifiedArgument(lazySpecification);
} else {
assert (type is JValueModifier);
assert (is ValueArgument valueArgument = inlineDefinitionArgumentToCeylon(specifiedArgument, update));
assert (is LazySpecifier definition = valueArgument.definition);
value lazySpecification = LazySpecification {
name = valueArgument.name;
parameterLists = [];
specifier = definition;
};
update(specifiedArgument, lazySpecification);
result = SpecifiedArgument(lazySpecification);
}
}
update(specifiedArgument, result);
return result;
}
"Compiles the given [[code]] for a Specified Argument
into a [[SpecifiedArgument]] using the Ceylon compiler
(more specifically, the rule for a `namedArgument`)."
shared SpecifiedArgument? compileSpecifiedArgument(String code, Anything(JNode,Node) update = noop) {
if (exists jNamedArgument = createParser(code).namedArgument()) {
try {
return specifiedArgumentToCeylon(jNamedArgument, update);
} catch (AssertionError e) {
return null;
}
} else {
return null;
}
}