KT-2298 js inter-module communication
This commit is contained in:
@@ -22,6 +22,7 @@ import com.google.common.base.Predicates;
|
|||||||
import com.google.common.collect.Iterables;
|
import com.google.common.collect.Iterables;
|
||||||
import com.intellij.openapi.Disposable;
|
import com.intellij.openapi.Disposable;
|
||||||
import com.intellij.openapi.project.Project;
|
import com.intellij.openapi.project.Project;
|
||||||
|
import com.intellij.openapi.util.io.FileUtil;
|
||||||
import com.intellij.psi.PsiFile;
|
import com.intellij.psi.PsiFile;
|
||||||
import jet.Function0;
|
import jet.Function0;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
@@ -40,6 +41,7 @@ import org.jetbrains.k2js.config.*;
|
|||||||
import org.jetbrains.k2js.facade.K2JSTranslator;
|
import org.jetbrains.k2js.facade.K2JSTranslator;
|
||||||
import org.jetbrains.k2js.facade.MainCallParameters;
|
import org.jetbrains.k2js.facade.MainCallParameters;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import static org.jetbrains.jet.cli.common.messages.CompilerMessageLocation.NO_LOCATION;
|
import static org.jetbrains.jet.cli.common.messages.CompilerMessageLocation.NO_LOCATION;
|
||||||
@@ -101,7 +103,6 @@ public class K2JSCompiler extends CLICompiler<K2JSCompilerArguments, K2JSCompile
|
|||||||
return ExitCode.INTERNAL_ERROR;
|
return ExitCode.INTERNAL_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
MainCallParameters mainCallParameters = arguments.createMainCallParameters();
|
MainCallParameters mainCallParameters = arguments.createMainCallParameters();
|
||||||
return translateAndGenerateOutputFile(mainCallParameters, messageCollector, environmentForJS, config, outputFile);
|
return translateAndGenerateOutputFile(mainCallParameters, messageCollector, environmentForJS, config, outputFile);
|
||||||
}
|
}
|
||||||
@@ -151,10 +152,11 @@ public class K2JSCompiler extends CLICompiler<K2JSCompilerArguments, K2JSCompile
|
|||||||
@NotNull
|
@NotNull
|
||||||
private static Config getConfig(@NotNull K2JSCompilerArguments arguments, @NotNull Project project) {
|
private static Config getConfig(@NotNull K2JSCompilerArguments arguments, @NotNull Project project) {
|
||||||
EcmaVersion ecmaVersion = EcmaVersion.fromString(arguments.target);
|
EcmaVersion ecmaVersion = EcmaVersion.fromString(arguments.target);
|
||||||
|
String moduleId = FileUtil.getNameWithoutExtension(new File(arguments.outputFile));
|
||||||
if (arguments.libraryFiles == null) {
|
if (arguments.libraryFiles == null) {
|
||||||
// lets discover the JS library definitions on the classpath
|
// lets discover the JS library definitions on the classpath
|
||||||
return new ClassPathLibraryDefintionsConfig(project, ecmaVersion);
|
return new ClassPathLibraryDefintionsConfig(project, moduleId, ecmaVersion);
|
||||||
}
|
}
|
||||||
return new LibrarySourcesConfig(project, arguments.libraryFiles, ecmaVersion);
|
return new LibrarySourcesConfig(project, moduleId, arguments.libraryFiles, ecmaVersion);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -174,10 +174,13 @@ public final class K2JSCompiler implements TranslatingCompiler {
|
|||||||
THashSet<Module> modules = new THashSet<Module>();
|
THashSet<Module> modules = new THashSet<Module>();
|
||||||
collectModuleDependencies(module, modules);
|
collectModuleDependencies(module, modules);
|
||||||
if (!modules.isEmpty()) {
|
if (!modules.isEmpty()) {
|
||||||
VirtualFile[] files = CompilerManager.getInstance(module.getProject()).createModulesCompileScope(
|
for (Module dependency : modules) {
|
||||||
modules.toArray(new Module[modules.size()]), false).getFiles(JetFileType.INSTANCE, true);
|
sb.append('@').append(dependency.getName()).append(',');
|
||||||
for (VirtualFile file : files) {
|
VirtualFile[] files = CompilerManager.getInstance(module.getProject()).createModuleCompileScope(dependency, false)
|
||||||
sb.append(file.getPath()).append(',');
|
.getFiles(JetFileType.INSTANCE, true);
|
||||||
|
for (VirtualFile file : files) {
|
||||||
|
sb.append(file.getPath()).append(',');
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -28,6 +28,6 @@ import static org.jetbrains.jet.plugin.project.JsModuleDetector.getLibLocationAn
|
|||||||
*/
|
*/
|
||||||
public final class IDEAConfig extends LibrarySourcesConfig {
|
public final class IDEAConfig extends LibrarySourcesConfig {
|
||||||
public IDEAConfig(@NotNull Project project) {
|
public IDEAConfig(@NotNull Project project) {
|
||||||
super(project, getLibLocationAndTargetForProject(project).first, EcmaVersion.defaultVersion());
|
super(project, "default", getLibLocationAndTargetForProject(project).first, EcmaVersion.defaultVersion());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -42,7 +42,7 @@ public abstract class SingleFileTranslationTest extends BasicTest {
|
|||||||
runFunctionOutputTest(EcmaVersion.all(), kotlinFilename, namespaceName, functionName, expectedResult);
|
runFunctionOutputTest(EcmaVersion.all(), kotlinFilename, namespaceName, functionName, expectedResult);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void runFunctionOutputTest(@NotNull EnumSet<EcmaVersion> ecmaVersions, @NotNull String kotlinFilename,
|
protected void runFunctionOutputTest(@NotNull Iterable<EcmaVersion> ecmaVersions, @NotNull String kotlinFilename,
|
||||||
@NotNull String namespaceName,
|
@NotNull String namespaceName,
|
||||||
@NotNull String functionName,
|
@NotNull String functionName,
|
||||||
@NotNull Object expectedResult) throws Exception {
|
@NotNull Object expectedResult) throws Exception {
|
||||||
@@ -50,7 +50,7 @@ public abstract class SingleFileTranslationTest extends BasicTest {
|
|||||||
runRhinoTests(kotlinFilename, ecmaVersions, new RhinoFunctionResultChecker(namespaceName, functionName, expectedResult));
|
runRhinoTests(kotlinFilename, ecmaVersions, new RhinoFunctionResultChecker(namespaceName, functionName, expectedResult));
|
||||||
}
|
}
|
||||||
|
|
||||||
public void checkFooBoxIsTrue(@NotNull String filename, @NotNull EnumSet<EcmaVersion> ecmaVersions) throws Exception {
|
public void checkFooBoxIsTrue(@NotNull String filename, @NotNull Iterable<EcmaVersion> ecmaVersions) throws Exception {
|
||||||
runFunctionOutputTest(ecmaVersions, filename, "foo", "box", true);
|
runFunctionOutputTest(ecmaVersions, filename, "foo", "box", true);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -58,7 +58,7 @@ public abstract class SingleFileTranslationTest extends BasicTest {
|
|||||||
checkFooBoxIsTrue(getTestName(true) + ".kt", EcmaVersion.all());
|
checkFooBoxIsTrue(getTestName(true) + ".kt", EcmaVersion.all());
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void fooBoxTest(@NotNull EnumSet<EcmaVersion> ecmaVersions) throws Exception {
|
protected void fooBoxTest(@NotNull Iterable<EcmaVersion> ecmaVersions) throws Exception {
|
||||||
checkFooBoxIsTrue(getTestName(true) + ".kt", ecmaVersions);
|
checkFooBoxIsTrue(getTestName(true) + ".kt", ecmaVersions);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -84,7 +84,7 @@ public abstract class SingleFileTranslationTest extends BasicTest {
|
|||||||
runRhinoTests(kotlinFilename, ecmaVersions, new RhinoSystemOutputChecker(expectedResult));
|
runRhinoTests(kotlinFilename, ecmaVersions, new RhinoSystemOutputChecker(expectedResult));
|
||||||
}
|
}
|
||||||
|
|
||||||
protected void performTestWithMain(@NotNull EnumSet<EcmaVersion> ecmaVersions,
|
protected void performTestWithMain(@NotNull Iterable<EcmaVersion> ecmaVersions,
|
||||||
@NotNull String testName,
|
@NotNull String testName,
|
||||||
@NotNull String testId,
|
@NotNull String testId,
|
||||||
@NotNull String... args) throws Exception {
|
@NotNull String... args) throws Exception {
|
||||||
|
|||||||
@@ -41,7 +41,7 @@ public final class TestConfig extends Config {
|
|||||||
private /*var*/ List<JetFile> jsLibFiles = null;
|
private /*var*/ List<JetFile> jsLibFiles = null;
|
||||||
|
|
||||||
public TestConfig(@NotNull Project project, @NotNull EcmaVersion version) {
|
public TestConfig(@NotNull Project project, @NotNull EcmaVersion version) {
|
||||||
super(project, version);
|
super(project, "main", version);
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
|
|||||||
@@ -39,11 +39,6 @@ class RhinoFunctionManager {
|
|||||||
this.functionName = functionName;
|
this.functionName = functionName;
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
|
||||||
public String getFunctionName() {
|
|
||||||
return functionName;
|
|
||||||
}
|
|
||||||
|
|
||||||
private Script compileScript(int optimizationLevel) {
|
private Script compileScript(int optimizationLevel) {
|
||||||
long startNano = System.nanoTime();
|
long startNano = System.nanoTime();
|
||||||
Context context = Context.enter();
|
Context context = Context.enter();
|
||||||
|
|||||||
@@ -17,6 +17,7 @@
|
|||||||
package org.jetbrains.k2js.test.rhino;
|
package org.jetbrains.k2js.test.rhino;
|
||||||
|
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
|
import org.jetbrains.k2js.translate.context.Namer;
|
||||||
import org.mozilla.javascript.Context;
|
import org.mozilla.javascript.Context;
|
||||||
import org.mozilla.javascript.Scriptable;
|
import org.mozilla.javascript.Scriptable;
|
||||||
|
|
||||||
@@ -59,10 +60,14 @@ public class RhinoFunctionResultChecker implements RhinoResultChecker {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private String functionCallString() {
|
private String functionCallString() {
|
||||||
String result = functionName + "()";
|
StringBuilder sb = new StringBuilder();
|
||||||
if (namespaceName != null) {
|
if (namespaceName != null) {
|
||||||
result = "Kotlin.defs." + namespaceName + "." + result;
|
sb.append("Kotlin.modules.main");
|
||||||
|
if (namespaceName != Namer.getRootNamespaceName()) {
|
||||||
|
sb.append('.').append(namespaceName);
|
||||||
|
}
|
||||||
|
sb.append('.');
|
||||||
}
|
}
|
||||||
return result;
|
return sb.append(functionName).append("()").toString();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -26,7 +26,6 @@ import org.jetbrains.k2js.test.BasicTest;
|
|||||||
import org.mozilla.javascript.*;
|
import org.mozilla.javascript.*;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileReader;
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
@@ -49,12 +48,7 @@ public final class RhinoUtils {
|
|||||||
new Supplier<String>() {
|
new Supplier<String>() {
|
||||||
@Override
|
@Override
|
||||||
public String get() {
|
public String get() {
|
||||||
try {
|
return fileToString(BasicTest.JSLINT_LIB);
|
||||||
return FileUtil.loadFile(new File(BasicTest.JSLINT_LIB));
|
|
||||||
}
|
|
||||||
catch (IOException e) {
|
|
||||||
throw new RuntimeException(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"JSLINT"
|
"JSLINT"
|
||||||
@@ -64,15 +58,19 @@ public final class RhinoUtils {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static String fileToString(String file) {
|
||||||
|
try {
|
||||||
|
return FileUtil.loadFile(new File(file));
|
||||||
|
}
|
||||||
|
catch (IOException e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private static void runFileWithRhino(@NotNull String inputFile,
|
private static void runFileWithRhino(@NotNull String inputFile,
|
||||||
@NotNull Context context,
|
@NotNull Context context,
|
||||||
@NotNull Scriptable scope) throws Exception {
|
@NotNull Scriptable scope) throws Exception {
|
||||||
FileReader reader = new FileReader(inputFile);
|
context.evaluateString(scope, fileToString(inputFile), inputFile, 1, null);
|
||||||
try {
|
|
||||||
context.evaluateReader(scope, reader, inputFile, 1, null);
|
|
||||||
} finally {
|
|
||||||
reader.close();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void runRhinoTest(@NotNull List<String> fileNames,
|
public static void runRhinoTest(@NotNull List<String> fileNames,
|
||||||
|
|||||||
@@ -18,7 +18,6 @@ package org.jetbrains.k2js.analyze;
|
|||||||
|
|
||||||
import com.google.common.base.Predicate;
|
import com.google.common.base.Predicate;
|
||||||
import com.google.common.base.Predicates;
|
import com.google.common.base.Predicates;
|
||||||
import com.google.common.collect.Sets;
|
|
||||||
import com.intellij.openapi.project.Project;
|
import com.intellij.openapi.project.Project;
|
||||||
import com.intellij.psi.PsiFile;
|
import com.intellij.psi.PsiFile;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
@@ -39,10 +38,10 @@ import org.jetbrains.jet.lang.resolve.scopes.WritableScope;
|
|||||||
import org.jetbrains.jet.lang.types.lang.JetStandardClasses;
|
import org.jetbrains.jet.lang.types.lang.JetStandardClasses;
|
||||||
import org.jetbrains.k2js.config.Config;
|
import org.jetbrains.k2js.config.Config;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Set;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Pavel Talanov
|
* @author Pavel Talanov
|
||||||
@@ -125,7 +124,7 @@ public final class AnalyzerFacadeForJS {
|
|||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static Collection<JetFile> withJsLibAdded(@NotNull Collection<JetFile> files, @NotNull Config config) {
|
public static Collection<JetFile> withJsLibAdded(@NotNull Collection<JetFile> files, @NotNull Config config) {
|
||||||
Set<JetFile> allFiles = Sets.newHashSet();
|
Collection<JetFile> allFiles = new ArrayList<JetFile>();
|
||||||
allFiles.addAll(files);
|
allFiles.addAll(files);
|
||||||
allFiles.addAll(config.getLibFiles());
|
allFiles.addAll(config.getLibFiles());
|
||||||
return allFiles;
|
return allFiles;
|
||||||
|
|||||||
+2
-2
@@ -28,8 +28,8 @@ import java.util.*;
|
|||||||
public class ClassPathLibraryDefintionsConfig extends Config {
|
public class ClassPathLibraryDefintionsConfig extends Config {
|
||||||
public static final String META_INF_SERVICES_FILE = "META-INF/services/org.jetbrains.kotlin.js.libraryDefinitions";
|
public static final String META_INF_SERVICES_FILE = "META-INF/services/org.jetbrains.kotlin.js.libraryDefinitions";
|
||||||
|
|
||||||
public ClassPathLibraryDefintionsConfig(@NotNull Project project, @NotNull EcmaVersion version) {
|
public ClassPathLibraryDefintionsConfig(@NotNull Project project, @NotNull String moduleId, @NotNull EcmaVersion version) {
|
||||||
super(project, version);
|
super(project, moduleId, version);
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
|
|||||||
@@ -34,7 +34,7 @@ public abstract class Config {
|
|||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static Config getEmptyConfig(@NotNull Project project, @NotNull EcmaVersion ecmaVersion) {
|
public static Config getEmptyConfig(@NotNull Project project, @NotNull EcmaVersion ecmaVersion) {
|
||||||
return new Config(project, ecmaVersion) {
|
return new Config(project, "main", ecmaVersion) {
|
||||||
@NotNull
|
@NotNull
|
||||||
@Override
|
@Override
|
||||||
protected List<JetFile> generateLibFiles() {
|
protected List<JetFile> generateLibFiles() {
|
||||||
@@ -117,9 +117,13 @@ public abstract class Config {
|
|||||||
@NotNull
|
@NotNull
|
||||||
private final EcmaVersion target;
|
private final EcmaVersion target;
|
||||||
|
|
||||||
public Config(@NotNull Project project, @NotNull EcmaVersion ecmaVersion) {
|
@NotNull
|
||||||
|
private final String moduleId;
|
||||||
|
|
||||||
|
public Config(@NotNull Project project, @NotNull String moduleId, @NotNull EcmaVersion ecmaVersion) {
|
||||||
this.project = project;
|
this.project = project;
|
||||||
this.target = ecmaVersion;
|
this.target = ecmaVersion;
|
||||||
|
this.moduleId = moduleId;
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
@@ -132,6 +136,11 @@ public abstract class Config {
|
|||||||
return target;
|
return target;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
public String getModuleId() {
|
||||||
|
return moduleId;
|
||||||
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
protected abstract List<JetFile> generateLibFiles();
|
protected abstract List<JetFile> generateLibFiles();
|
||||||
|
|
||||||
|
|||||||
@@ -39,13 +39,17 @@ import java.util.zip.ZipFile;
|
|||||||
* @author Pavel Talanov
|
* @author Pavel Talanov
|
||||||
*/
|
*/
|
||||||
public class LibrarySourcesConfig extends Config {
|
public class LibrarySourcesConfig extends Config {
|
||||||
public static final Key<Boolean> EXTERNAL_LIB = new Key<Boolean>("externalLib");
|
public static final Key<String> EXTERNAL_MODULE_NAME = new Key<String>("externalModule");
|
||||||
|
public static final String UNKNOWN_EXTERNAL_MODULE_NAME = "<unknown>";
|
||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
private final String[] files;
|
private final String[] files;
|
||||||
|
|
||||||
public LibrarySourcesConfig(@NotNull Project project, @Nullable String[] files, @NotNull EcmaVersion ecmaVersion) {
|
public LibrarySourcesConfig(@NotNull Project project,
|
||||||
super(project, ecmaVersion);
|
@NotNull String moduleId,
|
||||||
|
@Nullable String[] files,
|
||||||
|
@NotNull EcmaVersion ecmaVersion) {
|
||||||
|
super(project, moduleId, ecmaVersion);
|
||||||
this.files = files;
|
this.files = files;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -57,16 +61,22 @@ public class LibrarySourcesConfig extends Config {
|
|||||||
}
|
}
|
||||||
|
|
||||||
List<JetFile> jetFiles = new ArrayList<JetFile>();
|
List<JetFile> jetFiles = new ArrayList<JetFile>();
|
||||||
|
String moduleName = UNKNOWN_EXTERNAL_MODULE_NAME;
|
||||||
for (String path : files) {
|
for (String path : files) {
|
||||||
File file = new File(path);
|
File file = new File(path);
|
||||||
try {
|
try {
|
||||||
String name = file.getName();
|
String name = file.getName();
|
||||||
|
if (path.charAt(0) == '@') {
|
||||||
|
moduleName = path.substring(1);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
if (name.endsWith(".jar") || name.endsWith(".zip")) {
|
if (name.endsWith(".jar") || name.endsWith(".zip")) {
|
||||||
jetFiles.addAll(readZip(file));
|
jetFiles.addAll(readZip(file));
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
JetFile psiFile = JetFileUtils.createPsiFile(path, FileUtil.loadFile(file), getProject());
|
JetFile psiFile = JetFileUtils.createPsiFile(path, FileUtil.loadFile(file), getProject());
|
||||||
psiFile.putUserData(EXTERNAL_LIB, true);
|
psiFile.putUserData(EXTERNAL_MODULE_NAME, moduleName);
|
||||||
jetFiles.add(psiFile);
|
jetFiles.add(psiFile);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -98,7 +108,7 @@ public class LibrarySourcesConfig extends Config {
|
|||||||
InputStream stream = file.getInputStream(entry);
|
InputStream stream = file.getInputStream(entry);
|
||||||
String text = FileUtil.loadTextAndClose(stream);
|
String text = FileUtil.loadTextAndClose(stream);
|
||||||
JetFile jetFile = JetFileUtils.createPsiFile(entry.getName(), text, getProject());
|
JetFile jetFile = JetFileUtils.createPsiFile(entry.getName(), text, getProject());
|
||||||
jetFile.putUserData(EXTERNAL_LIB, true);
|
jetFile.putUserData(EXTERNAL_MODULE_NAME, UNKNOWN_EXTERNAL_MODULE_NAME);
|
||||||
result.add(jetFile);
|
result.add(jetFile);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -32,7 +32,6 @@ import org.jetbrains.k2js.utils.JetFileUtils;
|
|||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Collection;
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import static org.jetbrains.k2js.facade.FacadeUtils.parseString;
|
import static org.jetbrains.k2js.facade.FacadeUtils.parseString;
|
||||||
@@ -96,7 +95,7 @@ public final class K2JSTranslator {
|
|||||||
throws TranslationException {
|
throws TranslationException {
|
||||||
JetStandardLibrary.initialize(config.getProject());
|
JetStandardLibrary.initialize(config.getProject());
|
||||||
BindingContext bindingContext = AnalyzerFacadeForJS.analyzeFilesAndCheckErrors(filesToTranslate, config);
|
BindingContext bindingContext = AnalyzerFacadeForJS.analyzeFilesAndCheckErrors(filesToTranslate, config);
|
||||||
return Translation.generateAst(bindingContext, filesToTranslate, mainCallParameters, config.getTarget(), rawStatements);
|
return Translation.generateAst(bindingContext, filesToTranslate, mainCallParameters, config, rawStatements);
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
|
|||||||
@@ -32,14 +32,13 @@ public final class Namer {
|
|||||||
private static final String INITIALIZE_METHOD_NAME = "initialize";
|
private static final String INITIALIZE_METHOD_NAME = "initialize";
|
||||||
private static final String CLASS_OBJECT_NAME = "createClass";
|
private static final String CLASS_OBJECT_NAME = "createClass";
|
||||||
private static final String TRAIT_OBJECT_NAME = "createTrait";
|
private static final String TRAIT_OBJECT_NAME = "createTrait";
|
||||||
private static final String NAMESPACE_OBJECT_NAME = "createNamespace";
|
|
||||||
private static final String OBJECT_OBJECT_NAME = "createObject";
|
private static final String OBJECT_OBJECT_NAME = "createObject";
|
||||||
private static final String SETTER_PREFIX = "set_";
|
private static final String SETTER_PREFIX = "set_";
|
||||||
private static final String GETTER_PREFIX = "get_";
|
private static final String GETTER_PREFIX = "get_";
|
||||||
private static final String BACKING_FIELD_PREFIX = "$";
|
private static final String BACKING_FIELD_PREFIX = "$";
|
||||||
private static final String SUPER_METHOD_NAME = "super_init";
|
private static final String SUPER_METHOD_NAME = "super_init";
|
||||||
private static final String KOTLIN_OBJECT_NAME = "Kotlin";
|
private static final String KOTLIN_OBJECT_NAME = "Kotlin";
|
||||||
private static final String ROOT_NAMESPACE = "Root";
|
private static final String ROOT_NAMESPACE = "_";
|
||||||
private static final String RECEIVER_PARAMETER_NAME = "receiver";
|
private static final String RECEIVER_PARAMETER_NAME = "receiver";
|
||||||
private static final String CLASSES_OBJECT_NAME = "classes";
|
private static final String CLASSES_OBJECT_NAME = "classes";
|
||||||
private static final String THROW_NPE_FUN_NAME = "throwNPE";
|
private static final String THROW_NPE_FUN_NAME = "throwNPE";
|
||||||
@@ -112,7 +111,7 @@ public final class Namer {
|
|||||||
@NotNull
|
@NotNull
|
||||||
private final JsName traitName;
|
private final JsName traitName;
|
||||||
@NotNull
|
@NotNull
|
||||||
private final JsName namespaceName;
|
private final JsExpression definePackage;
|
||||||
@NotNull
|
@NotNull
|
||||||
private final JsName objectName;
|
private final JsName objectName;
|
||||||
|
|
||||||
@@ -129,7 +128,9 @@ public final class Namer {
|
|||||||
kotlinName = rootScope.declareName(KOTLIN_OBJECT_NAME);
|
kotlinName = rootScope.declareName(KOTLIN_OBJECT_NAME);
|
||||||
kotlinScope = new JsScope(rootScope, "Kotlin standard object");
|
kotlinScope = new JsScope(rootScope, "Kotlin standard object");
|
||||||
traitName = kotlinScope.declareName(TRAIT_OBJECT_NAME);
|
traitName = kotlinScope.declareName(TRAIT_OBJECT_NAME);
|
||||||
namespaceName = kotlinScope.declareName(NAMESPACE_OBJECT_NAME);
|
|
||||||
|
definePackage = kotlin("definePackage");
|
||||||
|
|
||||||
className = kotlinScope.declareName(CLASS_OBJECT_NAME);
|
className = kotlinScope.declareName(CLASS_OBJECT_NAME);
|
||||||
objectName = kotlinScope.declareName(OBJECT_OBJECT_NAME);
|
objectName = kotlinScope.declareName(OBJECT_OBJECT_NAME);
|
||||||
|
|
||||||
@@ -151,8 +152,8 @@ public final class Namer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public JsExpression namespaceCreationMethodReference() {
|
public JsExpression packageDefinitionMethodReference() {
|
||||||
return kotlin(namespaceName);
|
return definePackage;
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
@@ -169,14 +170,17 @@ public final class Namer {
|
|||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private JsExpression kotlin(@NotNull JsName name) {
|
private JsExpression kotlin(@NotNull JsName name) {
|
||||||
JsNameRef reference = name.makeRef();
|
return kotlin(name.makeRef());
|
||||||
reference.setQualifier(kotlinName.makeRef());
|
}
|
||||||
return reference;
|
|
||||||
|
@NotNull
|
||||||
|
public JsExpression kotlin(@NotNull String name) {
|
||||||
|
return kotlin(kotlinScope.declareName(name));
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private JsExpression kotlin(@NotNull JsExpression reference) {
|
private JsExpression kotlin(@NotNull JsExpression reference) {
|
||||||
setQualifier(reference, kotlinName.makeRef());
|
setQualifier(reference, kotlinObject());
|
||||||
return reference;
|
return reference;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -18,13 +18,17 @@ package org.jetbrains.k2js.translate.context;
|
|||||||
|
|
||||||
import com.google.common.collect.Maps;
|
import com.google.common.collect.Maps;
|
||||||
import com.google.dart.compiler.backend.js.ast.*;
|
import com.google.dart.compiler.backend.js.ast.*;
|
||||||
|
import com.intellij.psi.PsiElement;
|
||||||
|
import com.intellij.psi.PsiFile;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
import org.jetbrains.jet.lang.descriptors.*;
|
import org.jetbrains.jet.lang.descriptors.*;
|
||||||
import org.jetbrains.jet.lang.resolve.BindingContext;
|
import org.jetbrains.jet.lang.resolve.BindingContext;
|
||||||
|
import org.jetbrains.jet.lang.resolve.BindingContextUtils;
|
||||||
import org.jetbrains.jet.lang.resolve.DescriptorUtils;
|
import org.jetbrains.jet.lang.resolve.DescriptorUtils;
|
||||||
import org.jetbrains.jet.lang.types.lang.JetStandardLibrary;
|
import org.jetbrains.jet.lang.types.lang.JetStandardLibrary;
|
||||||
import org.jetbrains.k2js.config.EcmaVersion;
|
import org.jetbrains.k2js.config.EcmaVersion;
|
||||||
|
import org.jetbrains.k2js.config.LibrarySourcesConfig;
|
||||||
import org.jetbrains.k2js.translate.context.generator.Generator;
|
import org.jetbrains.k2js.translate.context.generator.Generator;
|
||||||
import org.jetbrains.k2js.translate.context.generator.Rule;
|
import org.jetbrains.k2js.translate.context.generator.Rule;
|
||||||
import org.jetbrains.k2js.translate.intrinsic.Intrinsics;
|
import org.jetbrains.k2js.translate.intrinsic.Intrinsics;
|
||||||
@@ -105,6 +109,11 @@ public final class StaticContext {
|
|||||||
return ecmaVersion == EcmaVersion.v5;
|
return ecmaVersion == EcmaVersion.v5;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
public EcmaVersion getEcmaVersion() {
|
||||||
|
return ecmaVersion;
|
||||||
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public JsProgram getProgram() {
|
public JsProgram getProgram() {
|
||||||
return program;
|
return program;
|
||||||
@@ -179,8 +188,16 @@ public final class StaticContext {
|
|||||||
if (!(descriptor instanceof NamespaceDescriptor)) {
|
if (!(descriptor instanceof NamespaceDescriptor)) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
String nameForNamespace = getNameForNamespace((NamespaceDescriptor) descriptor);
|
|
||||||
return getRootScope().declareUnobfuscatableName(nameForNamespace);
|
String name;
|
||||||
|
if (DescriptorUtils.isRootNamespace((NamespaceDescriptor) descriptor)) {
|
||||||
|
name = Namer.getRootNamespaceName();
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
name = descriptor.getName().getName();
|
||||||
|
}
|
||||||
|
|
||||||
|
return getRootScope().declareUnobfuscatableName(name);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
Rule<JsName> memberDeclarationsInsideParentsScope = new Rule<JsName>() {
|
Rule<JsName> memberDeclarationsInsideParentsScope = new Rule<JsName>() {
|
||||||
@@ -385,14 +402,50 @@ public final class StaticContext {
|
|||||||
Rule<JsNameRef> namespaceLevelDeclarationsHaveEnclosingNamespacesNamesAsQualifier = new Rule<JsNameRef>() {
|
Rule<JsNameRef> namespaceLevelDeclarationsHaveEnclosingNamespacesNamesAsQualifier = new Rule<JsNameRef>() {
|
||||||
@Override
|
@Override
|
||||||
public JsNameRef apply(@NotNull DeclarationDescriptor descriptor) {
|
public JsNameRef apply(@NotNull DeclarationDescriptor descriptor) {
|
||||||
DeclarationDescriptor containingDeclaration = getContainingDeclaration(descriptor);
|
DeclarationDescriptor containingDescriptor = getContainingDeclaration(descriptor);
|
||||||
if (!(containingDeclaration instanceof NamespaceDescriptor)) {
|
if (!(containingDescriptor instanceof NamespaceDescriptor)) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
JsName containingDeclarationName = getNameForDescriptor(containingDeclaration);
|
|
||||||
JsNameRef qualifier = containingDeclarationName.makeRef();
|
final JsNameRef result = new JsNameRef(getNameForDescriptor(containingDescriptor));
|
||||||
qualifier.setQualifier(getQualifierForDescriptor(containingDeclaration));
|
if (DescriptorUtils.isRootNamespace((NamespaceDescriptor) containingDescriptor)) {
|
||||||
return qualifier;
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
JsNameRef qualifier = result;
|
||||||
|
while ((containingDescriptor = getContainingDeclaration(containingDescriptor)) instanceof NamespaceDescriptor &&
|
||||||
|
!DescriptorUtils.isRootNamespace((NamespaceDescriptor) containingDescriptor)) {
|
||||||
|
JsNameRef ref = getNameForDescriptor(containingDescriptor).makeRef();
|
||||||
|
qualifier.setQualifier(ref);
|
||||||
|
qualifier = ref;
|
||||||
|
}
|
||||||
|
|
||||||
|
PsiElement element = BindingContextUtils.descriptorToDeclaration(bindingContext, descriptor);
|
||||||
|
if (element == null && descriptor instanceof PropertyAccessorDescriptor) {
|
||||||
|
element = BindingContextUtils.descriptorToDeclaration(bindingContext, ((PropertyAccessorDescriptor) descriptor)
|
||||||
|
.getCorrespondingProperty());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (element != null) {
|
||||||
|
PsiFile file = element.getContainingFile();
|
||||||
|
String moduleName = file.getUserData(LibrarySourcesConfig.EXTERNAL_MODULE_NAME);
|
||||||
|
if (LibrarySourcesConfig.UNKNOWN_EXTERNAL_MODULE_NAME.equals(moduleName)) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
else if (moduleName != null) {
|
||||||
|
qualifier.setQualifier(new JsArrayAccess(namer.kotlin("modules"), program.getStringLiteral(moduleName)));
|
||||||
|
}
|
||||||
|
else if (result == qualifier && result.getIdent().equals("kotlin")) {
|
||||||
|
// todo WebDemoExamples2Test#testBuilder, package "kotlin" from kotlin/js/js.libraries/src/stdlib/JUMaps.kt must be inlined
|
||||||
|
return qualifier;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (qualifier.getQualifier() == null) {
|
||||||
|
qualifier.setQualifier(new JsNameRef(Namer.getRootNamespaceName()));
|
||||||
|
}
|
||||||
|
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
Rule<JsNameRef> constructorHaveTheSameQualifierAsTheClass = new Rule<JsNameRef>() {
|
Rule<JsNameRef> constructorHaveTheSameQualifierAsTheClass = new Rule<JsNameRef>() {
|
||||||
@@ -448,10 +501,7 @@ public final class StaticContext {
|
|||||||
Rule<Boolean> topLevelNamespaceHaveNoQualifier = new Rule<Boolean>() {
|
Rule<Boolean> topLevelNamespaceHaveNoQualifier = new Rule<Boolean>() {
|
||||||
@Override
|
@Override
|
||||||
public Boolean apply(@NotNull DeclarationDescriptor descriptor) {
|
public Boolean apply(@NotNull DeclarationDescriptor descriptor) {
|
||||||
if (!(descriptor instanceof NamespaceDescriptor)) {
|
if (descriptor instanceof NamespaceDescriptor && DescriptorUtils.isRootNamespace((NamespaceDescriptor) descriptor)) {
|
||||||
return null;
|
|
||||||
}
|
|
||||||
if (DescriptorUtils.isTopLevelNamespace((NamespaceDescriptor) descriptor)) {
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return null;
|
return null;
|
||||||
|
|||||||
@@ -24,6 +24,7 @@ import org.jetbrains.jet.lang.descriptors.CallableDescriptor;
|
|||||||
import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor;
|
import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor;
|
||||||
import org.jetbrains.jet.lang.psi.JetExpression;
|
import org.jetbrains.jet.lang.psi.JetExpression;
|
||||||
import org.jetbrains.jet.lang.resolve.BindingContext;
|
import org.jetbrains.jet.lang.resolve.BindingContext;
|
||||||
|
import org.jetbrains.k2js.config.EcmaVersion;
|
||||||
import org.jetbrains.k2js.translate.intrinsic.Intrinsics;
|
import org.jetbrains.k2js.translate.intrinsic.Intrinsics;
|
||||||
|
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
@@ -58,6 +59,10 @@ public final class TranslationContext {
|
|||||||
return staticContext.isEcma5();
|
return staticContext.isEcma5();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public boolean isNotEcma3() {
|
||||||
|
return staticContext.getEcmaVersion() != EcmaVersion.v3;
|
||||||
|
}
|
||||||
|
|
||||||
private TranslationContext(@NotNull StaticContext staticContext,
|
private TranslationContext(@NotNull StaticContext staticContext,
|
||||||
@NotNull DynamicContext dynamicContext,
|
@NotNull DynamicContext dynamicContext,
|
||||||
@NotNull AliasingContext context) {
|
@NotNull AliasingContext context) {
|
||||||
|
|||||||
+11
-14
@@ -18,13 +18,11 @@ package org.jetbrains.k2js.translate.declaration;
|
|||||||
|
|
||||||
import com.google.common.collect.BiMap;
|
import com.google.common.collect.BiMap;
|
||||||
import com.google.common.collect.HashBiMap;
|
import com.google.common.collect.HashBiMap;
|
||||||
import com.google.common.collect.Lists;
|
|
||||||
import com.google.dart.compiler.backend.js.ast.*;
|
import com.google.dart.compiler.backend.js.ast.*;
|
||||||
import com.google.dart.compiler.util.AstUtil;
|
import com.google.dart.compiler.util.AstUtil;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
import org.jetbrains.jet.lang.descriptors.ClassDescriptor;
|
import org.jetbrains.jet.lang.descriptors.ClassDescriptor;
|
||||||
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
|
|
||||||
import org.jetbrains.jet.lang.psi.JetClass;
|
import org.jetbrains.jet.lang.psi.JetClass;
|
||||||
import org.jetbrains.k2js.translate.context.Namer;
|
import org.jetbrains.k2js.translate.context.Namer;
|
||||||
import org.jetbrains.k2js.translate.context.TranslationContext;
|
import org.jetbrains.k2js.translate.context.TranslationContext;
|
||||||
@@ -32,12 +30,12 @@ import org.jetbrains.k2js.translate.general.AbstractTranslator;
|
|||||||
import org.jetbrains.k2js.translate.general.Translation;
|
import org.jetbrains.k2js.translate.general.Translation;
|
||||||
import org.jetbrains.k2js.translate.utils.BindingUtils;
|
import org.jetbrains.k2js.translate.utils.BindingUtils;
|
||||||
import org.jetbrains.k2js.translate.utils.ClassSortingUtils;
|
import org.jetbrains.k2js.translate.utils.ClassSortingUtils;
|
||||||
|
import org.jetbrains.k2js.translate.utils.JsAstUtils;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import static org.jetbrains.k2js.translate.utils.JsAstUtils.*;
|
import static org.jetbrains.k2js.translate.utils.JsAstUtils.*;
|
||||||
import static org.jetbrains.k2js.translate.utils.JsDescriptorUtils.getAllClassesDefinedInNamespace;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Pavel Talanov
|
* @author Pavel Talanov
|
||||||
@@ -142,18 +140,17 @@ public final class ClassDeclarationTranslator extends AbstractTranslator {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public List<JsPropertyInitializer> classDeclarationsForNamespace(@NotNull NamespaceDescriptor namespaceDescriptor) {
|
public JsPropertyInitializer getClassNameToClassObject(@NotNull ClassDescriptor classDescriptor) {
|
||||||
List<JsPropertyInitializer> result = Lists.newArrayList();
|
|
||||||
for (ClassDescriptor classDescriptor : getAllClassesDefinedInNamespace(namespaceDescriptor, bindingContext())) {
|
|
||||||
result.add(getClassNameToClassObject(classDescriptor));
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
@NotNull
|
|
||||||
private JsPropertyInitializer getClassNameToClassObject(@NotNull ClassDescriptor classDescriptor) {
|
|
||||||
JsName className = context().getNameForDescriptor(classDescriptor);
|
JsName className = context().getNameForDescriptor(classDescriptor);
|
||||||
JsNameRef alreadyDefinedClassReference = qualified(className, getDeclarationsObjectName().makeRef());
|
JsNameRef alreadyDefinedClassReference = qualified(className, getDeclarationsObjectName().makeRef());
|
||||||
return new JsPropertyInitializer(className.makeRef(), alreadyDefinedClassReference);
|
JsExpression value;
|
||||||
|
if (context().isEcma5()) {
|
||||||
|
value = JsAstUtils.createDataDescriptor(alreadyDefinedClassReference, false, context());
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
value = alreadyDefinedClassReference;
|
||||||
|
}
|
||||||
|
|
||||||
|
return new JsPropertyInitializer(className.makeRef(), value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+20
-2
@@ -19,6 +19,8 @@ package org.jetbrains.k2js.translate.declaration;
|
|||||||
import com.google.dart.compiler.backend.js.ast.JsExpression;
|
import com.google.dart.compiler.backend.js.ast.JsExpression;
|
||||||
import com.google.dart.compiler.backend.js.ast.JsPropertyInitializer;
|
import com.google.dart.compiler.backend.js.ast.JsPropertyInitializer;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
import org.jetbrains.annotations.Nullable;
|
||||||
|
import org.jetbrains.jet.lang.descriptors.ClassDescriptor;
|
||||||
import org.jetbrains.jet.lang.descriptors.FunctionDescriptor;
|
import org.jetbrains.jet.lang.descriptors.FunctionDescriptor;
|
||||||
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
|
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
|
||||||
import org.jetbrains.jet.lang.descriptors.PropertyDescriptor;
|
import org.jetbrains.jet.lang.descriptors.PropertyDescriptor;
|
||||||
@@ -39,6 +41,17 @@ import static org.jetbrains.k2js.translate.utils.BindingUtils.*;
|
|||||||
* @author Pavel Talanov
|
* @author Pavel Talanov
|
||||||
*/
|
*/
|
||||||
public final class DeclarationBodyVisitor extends TranslatorVisitor<List<JsPropertyInitializer>> {
|
public final class DeclarationBodyVisitor extends TranslatorVisitor<List<JsPropertyInitializer>> {
|
||||||
|
@Nullable
|
||||||
|
private final ClassDeclarationTranslator classDeclarationTranslator;
|
||||||
|
|
||||||
|
public DeclarationBodyVisitor() {
|
||||||
|
classDeclarationTranslator = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public DeclarationBodyVisitor(ClassDeclarationTranslator classDeclarationTranslator) {
|
||||||
|
this.classDeclarationTranslator = classDeclarationTranslator;
|
||||||
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public List<JsPropertyInitializer> traverseClass(@NotNull JetClassOrObject jetClass,
|
public List<JsPropertyInitializer> traverseClass(@NotNull JetClassOrObject jetClass,
|
||||||
@NotNull TranslationContext context) {
|
@NotNull TranslationContext context) {
|
||||||
@@ -51,7 +64,7 @@ public final class DeclarationBodyVisitor extends TranslatorVisitor<List<JsPrope
|
|||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public List<JsPropertyInitializer> traverseNamespace(@NotNull NamespaceDescriptor namespace,
|
public List<JsPropertyInitializer> traverseNamespace(@NotNull NamespaceDescriptor namespace,
|
||||||
@NotNull TranslationContext context) {
|
@NotNull TranslationContext context) {
|
||||||
List<JsPropertyInitializer> properties = new ArrayList<JsPropertyInitializer>();
|
List<JsPropertyInitializer> properties = new ArrayList<JsPropertyInitializer>();
|
||||||
for (JetDeclaration declaration : getDeclarationsForNamespace(context.bindingContext(), namespace)) {
|
for (JetDeclaration declaration : getDeclarationsForNamespace(context.bindingContext(), namespace)) {
|
||||||
properties.addAll(declaration.accept(this, context));
|
properties.addAll(declaration.accept(this, context));
|
||||||
@@ -62,7 +75,12 @@ public final class DeclarationBodyVisitor extends TranslatorVisitor<List<JsPrope
|
|||||||
@Override
|
@Override
|
||||||
@NotNull
|
@NotNull
|
||||||
public List<JsPropertyInitializer> visitClass(@NotNull JetClass expression, @NotNull TranslationContext context) {
|
public List<JsPropertyInitializer> visitClass(@NotNull JetClass expression, @NotNull TranslationContext context) {
|
||||||
return Collections.emptyList();
|
if (classDeclarationTranslator == null) {
|
||||||
|
return Collections.emptyList();
|
||||||
|
}
|
||||||
|
|
||||||
|
ClassDescriptor classDescriptor = getClassDescriptor(context.bindingContext(), expression);
|
||||||
|
return Collections.singletonList(classDeclarationTranslator.getClassNameToClassObject(classDescriptor));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|||||||
+23
-29
@@ -24,12 +24,10 @@ import org.jetbrains.jet.lang.descriptors.ClassDescriptor;
|
|||||||
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
|
import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
|
||||||
import org.jetbrains.jet.lang.psi.JetFile;
|
import org.jetbrains.jet.lang.psi.JetFile;
|
||||||
import org.jetbrains.jet.lang.resolve.DescriptorUtils;
|
import org.jetbrains.jet.lang.resolve.DescriptorUtils;
|
||||||
import org.jetbrains.k2js.translate.context.Namer;
|
|
||||||
import org.jetbrains.k2js.translate.context.TranslationContext;
|
import org.jetbrains.k2js.translate.context.TranslationContext;
|
||||||
import org.jetbrains.k2js.translate.general.AbstractTranslator;
|
import org.jetbrains.k2js.translate.general.AbstractTranslator;
|
||||||
import org.jetbrains.k2js.translate.utils.JsAstUtils;
|
import org.jetbrains.k2js.translate.utils.JsAstUtils;
|
||||||
import org.jetbrains.k2js.translate.utils.JsDescriptorUtils;
|
import org.jetbrains.k2js.translate.utils.JsDescriptorUtils;
|
||||||
import org.jetbrains.k2js.translate.utils.TranslationUtils;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
@@ -37,7 +35,6 @@ import java.util.Set;
|
|||||||
|
|
||||||
import static org.jetbrains.k2js.translate.utils.BindingUtils.getAllNonNativeNamespaceDescriptors;
|
import static org.jetbrains.k2js.translate.utils.BindingUtils.getAllNonNativeNamespaceDescriptors;
|
||||||
import static org.jetbrains.k2js.translate.utils.JsDescriptorUtils.getAllClassesDefinedInNamespace;
|
import static org.jetbrains.k2js.translate.utils.JsDescriptorUtils.getAllClassesDefinedInNamespace;
|
||||||
import static org.jetbrains.k2js.translate.utils.JsAstUtils.setQualifier;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Pavel Talanov
|
* @author Pavel Talanov
|
||||||
@@ -85,8 +82,8 @@ public final class NamespaceDeclarationTranslator extends AbstractTranslator {
|
|||||||
|
|
||||||
private void namespacesDeclarations(List<JsStatement> statements) {
|
private void namespacesDeclarations(List<JsStatement> statements) {
|
||||||
List<NamespaceTranslator> namespaceTranslators = getTranslatorsForNonEmptyNamespaces();
|
List<NamespaceTranslator> namespaceTranslators = getTranslatorsForNonEmptyNamespaces();
|
||||||
statements.addAll(declarationStatements(namespaceTranslators, context()));
|
declarationStatements(namespaceTranslators, statements);
|
||||||
statements.addAll(initializeStatements());
|
initializeStatements(namespaceTranslators, statements);
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
@@ -98,34 +95,31 @@ public final class NamespaceDeclarationTranslator extends AbstractTranslator {
|
|||||||
return namespaceTranslators;
|
return namespaceTranslators;
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
private void declarationStatements(@NotNull List<NamespaceTranslator> namespaceTranslators,
|
||||||
private static List<JsStatement> declarationStatements(@NotNull List<NamespaceTranslator> namespaceTranslators, TranslationContext context) {
|
@NotNull List<JsStatement> statements) {
|
||||||
List<JsStatement> result = Lists.newArrayList();
|
JsObjectLiteral objectLiteral = new JsObjectLiteral();
|
||||||
|
JsNameRef packageMapNameRef = context().jsScope().declareName("_").makeRef();
|
||||||
JsNameRef defs = JsAstUtils.qualified(context.jsScope().declareName("defs"), context.namer().kotlinObject());
|
JsExpression packageMapValue;
|
||||||
for (NamespaceTranslator translator : namespaceTranslators) {
|
if (context().isNotEcma3()) {
|
||||||
JsVars vars = translator.getDeclarationAsVar();
|
packageMapValue = AstUtil.newInvocation(JsAstUtils.CREATE_OBJECT, context().program().getNullLiteral(), objectLiteral);
|
||||||
|
}
|
||||||
JsVars.JsVar var = vars.iterator().next();
|
else {
|
||||||
JsNameRef ref = new JsNameRef(var.getName());
|
packageMapValue = objectLiteral;
|
||||||
ref.setQualifier(defs);
|
}
|
||||||
|
statements.add(JsAstUtils.newVar(packageMapNameRef.getName(), packageMapValue));
|
||||||
result.add(vars);
|
|
||||||
result.add(JsAstUtils.assignment(ref, new JsNameRef(var.getName())).makeStmt());
|
for (NamespaceTranslator translator : namespaceTranslators) {
|
||||||
|
translator.addNamespaceDeclaration(objectLiteral.getPropertyInitializers());
|
||||||
}
|
}
|
||||||
return result;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
private static void initializeStatements(@NotNull List<NamespaceTranslator> namespaceTranslators,
|
||||||
private List<JsStatement> initializeStatements() {
|
@NotNull List<JsStatement> statements) {
|
||||||
List<JsStatement> result = Lists.newArrayList();
|
for (NamespaceTranslator translator : namespaceTranslators) {
|
||||||
for (NamespaceDescriptor descriptor : filterNonEmptyNamespaces(namespaceDescriptors)) {
|
for (JsExpression expression : translator.getInitializers()) {
|
||||||
JsNameRef initializeMethodReference = Namer.initializeMethodReference();
|
statements.add(expression.makeStmt());
|
||||||
JsNameRef fqNamespaceNameRef = TranslationUtils.getQualifiedReference(context(), descriptor);
|
}
|
||||||
setQualifier(initializeMethodReference, fqNamespaceNameRef);
|
|
||||||
result.add(AstUtil.newInvocation(initializeMethodReference).makeStmt());
|
|
||||||
}
|
}
|
||||||
return result;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
|
|||||||
+47
-44
@@ -25,15 +25,14 @@ import org.jetbrains.jet.lang.resolve.DescriptorUtils;
|
|||||||
import org.jetbrains.k2js.translate.context.TranslationContext;
|
import org.jetbrains.k2js.translate.context.TranslationContext;
|
||||||
import org.jetbrains.k2js.translate.general.AbstractTranslator;
|
import org.jetbrains.k2js.translate.general.AbstractTranslator;
|
||||||
import org.jetbrains.k2js.translate.general.Translation;
|
import org.jetbrains.k2js.translate.general.Translation;
|
||||||
import org.jetbrains.k2js.translate.initializer.InitializerUtils;
|
import org.jetbrains.k2js.translate.utils.JsAstUtils;
|
||||||
import org.jetbrains.k2js.translate.utils.JsDescriptorUtils;
|
import org.jetbrains.k2js.translate.utils.JsDescriptorUtils;
|
||||||
|
import org.jetbrains.k2js.translate.utils.TranslationUtils;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collections;
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import static org.jetbrains.k2js.translate.utils.JsAstUtils.newObjectLiteral;
|
import static org.jetbrains.k2js.translate.utils.JsAstUtils.newObjectLiteral;
|
||||||
import static org.jetbrains.k2js.translate.utils.JsAstUtils.newVar;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Pavel.Talanov
|
* @author Pavel.Talanov
|
||||||
@@ -49,6 +48,9 @@ public final class NamespaceTranslator extends AbstractTranslator {
|
|||||||
@NotNull
|
@NotNull
|
||||||
private final ClassDeclarationTranslator classDeclarationTranslator;
|
private final ClassDeclarationTranslator classDeclarationTranslator;
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
private final List<JsExpression> initializers = new ArrayList<JsExpression>();
|
||||||
|
|
||||||
/*package*/ NamespaceTranslator(@NotNull NamespaceDescriptor descriptor,
|
/*package*/ NamespaceTranslator(@NotNull NamespaceDescriptor descriptor,
|
||||||
@NotNull ClassDeclarationTranslator classDeclarationTranslator,
|
@NotNull ClassDeclarationTranslator classDeclarationTranslator,
|
||||||
@NotNull TranslationContext context) {
|
@NotNull TranslationContext context) {
|
||||||
@@ -58,80 +60,81 @@ public final class NamespaceTranslator extends AbstractTranslator {
|
|||||||
this.classDeclarationTranslator = classDeclarationTranslator;
|
this.classDeclarationTranslator = classDeclarationTranslator;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public JsVars getDeclarationAsVar() {
|
public List<JsExpression> getInitializers() {
|
||||||
return newVar(namespaceName, getNamespaceDeclaration());
|
return initializers;
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public JsPropertyInitializer getDeclarationAsInitializer() {
|
public JsPropertyInitializer getDeclarationAsInitializer() {
|
||||||
|
addNamespaceInitializer();
|
||||||
return new JsPropertyInitializer(namespaceName.makeRef(), getNamespaceDeclaration());
|
return new JsPropertyInitializer(namespaceName.makeRef(), getNamespaceDeclaration());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void addNamespaceDeclaration(List<JsPropertyInitializer> list) {
|
||||||
|
addNamespaceInitializer();
|
||||||
|
|
||||||
|
if (DescriptorUtils.isRootNamespace(descriptor)) {
|
||||||
|
list.addAll(getFunctionsAndClasses());
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
JsExpression value = getNamespaceDeclaration();
|
||||||
|
if (context().isNotEcma3()) {
|
||||||
|
value = JsAstUtils.createDataDescriptor(value, false, context());
|
||||||
|
}
|
||||||
|
|
||||||
|
list.add(new JsPropertyInitializer(namespaceName.makeRef(), value));
|
||||||
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private JsInvocation getNamespaceDeclaration() {
|
private JsInvocation getNamespaceDeclaration() {
|
||||||
JsInvocation namespaceDeclaration = namespaceCreateMethodInvocation();
|
JsInvocation namespaceDeclaration = namespaceCreateMethodInvocation();
|
||||||
addNamespaceInitializersAndProperties(namespaceDeclaration);
|
addIfNeed(getFunctionsAndClasses(), namespaceDeclaration.getArguments());
|
||||||
namespaceDeclaration.getArguments().add(getClassesAndNestedNamespaces());
|
addIfNeed(getNestedNamespaceDeclarations(), namespaceDeclaration.getArguments());
|
||||||
return namespaceDeclaration;
|
return namespaceDeclaration;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void addNamespaceInitializersAndProperties(@NotNull JsInvocation namespaceDeclaration) {
|
private void addNamespaceInitializer() {
|
||||||
JsFunction initializer = Translation.generateNamespaceInitializerMethod(descriptor, context());
|
JsFunction initializer = Translation.generateNamespaceInitializerMethod(descriptor, context());
|
||||||
List<JsPropertyInitializer> properties = new DeclarationBodyVisitor().traverseNamespace(descriptor, context());
|
if (!initializer.getBody().getStatements().isEmpty()) {
|
||||||
if (context().isEcma5()) {
|
JsNameRef call = new JsNameRef("call");
|
||||||
addEcma5InitializersAndProperties(namespaceDeclaration.getArguments(), initializer, properties);
|
call.setQualifier(initializer);
|
||||||
}
|
JsInvocation invocation = new JsInvocation();
|
||||||
else {
|
invocation.setQualifier(call);
|
||||||
addEcma3InitializersAndProperties(namespaceDeclaration, initializer, properties);
|
invocation.getArguments().add(TranslationUtils.getQualifiedReference(context(), descriptor));
|
||||||
|
initializers.add(invocation);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void addEcma3InitializersAndProperties(@NotNull JsInvocation namespaceDeclaration,
|
private List<JsPropertyInitializer> getFunctionsAndClasses() {
|
||||||
@NotNull JsFunction initializer,
|
return new DeclarationBodyVisitor(classDeclarationTranslator).traverseNamespace(descriptor, context());
|
||||||
@NotNull List<JsPropertyInitializer> properties) {
|
|
||||||
List<JsPropertyInitializer> propertyList = new ArrayList<JsPropertyInitializer>();
|
|
||||||
propertyList.add(InitializerUtils.generateInitializeMethod(initializer));
|
|
||||||
propertyList.addAll(properties);
|
|
||||||
namespaceDeclaration.getArguments().add(newObjectLiteral(propertyList));
|
|
||||||
}
|
|
||||||
|
|
||||||
private void addEcma5InitializersAndProperties(@NotNull List<JsExpression> expressions,
|
|
||||||
@NotNull JsFunction initializer,
|
|
||||||
@NotNull List<JsPropertyInitializer> properties) {
|
|
||||||
expressions.add(initializer.getBody().getStatements().isEmpty() ? context().program().getNullLiteral() : initializer);
|
|
||||||
expressions.add(properties.isEmpty() ? context().program().getNullLiteral() : newObjectLiteral(properties));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private JsInvocation namespaceCreateMethodInvocation() {
|
private JsInvocation namespaceCreateMethodInvocation() {
|
||||||
return AstUtil.newInvocation(context().namer().namespaceCreationMethodReference());
|
return AstUtil.newInvocation(context().namer().packageDefinitionMethodReference());
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
private void addIfNeed(@NotNull List<JsPropertyInitializer> declarations, @NotNull List<JsExpression> expressions) {
|
||||||
private JsObjectLiteral getClassesAndNestedNamespaces() {
|
// ecma5 expects strict number of arguments, but ecma3 doesn't
|
||||||
JsObjectLiteral classesAndNestedNamespaces = new JsObjectLiteral();
|
if (!declarations.isEmpty()) {
|
||||||
classesAndNestedNamespaces.getPropertyInitializers().addAll(getClassesDefined());
|
expressions.add(newObjectLiteral(declarations));
|
||||||
classesAndNestedNamespaces.getPropertyInitializers().addAll(getNestedNamespaceDeclarations());
|
}
|
||||||
return classesAndNestedNamespaces;
|
else if (context().isNotEcma3()) {
|
||||||
}
|
expressions.add(context().program().getNullLiteral());
|
||||||
|
}
|
||||||
@NotNull
|
|
||||||
private List<JsPropertyInitializer> getClassesDefined() {
|
|
||||||
return classDeclarationTranslator.classDeclarationsForNamespace(descriptor);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private List<JsPropertyInitializer> getNestedNamespaceDeclarations() {
|
private List<JsPropertyInitializer> getNestedNamespaceDeclarations() {
|
||||||
if (DescriptorUtils.isRootNamespace(descriptor)) {
|
|
||||||
return Collections.emptyList();
|
|
||||||
}
|
|
||||||
List<JsPropertyInitializer> result = Lists.newArrayList();
|
List<JsPropertyInitializer> result = Lists.newArrayList();
|
||||||
List<NamespaceDescriptor> nestedNamespaces = JsDescriptorUtils.getNestedNamespaces(descriptor, context().bindingContext());
|
List<NamespaceDescriptor> nestedNamespaces = JsDescriptorUtils.getNestedNamespaces(descriptor, context().bindingContext());
|
||||||
for (NamespaceDescriptor nestedNamespace : nestedNamespaces) {
|
for (NamespaceDescriptor nestedNamespace : nestedNamespaces) {
|
||||||
NamespaceTranslator nestedNamespaceTranslator = new NamespaceTranslator(nestedNamespace, classDeclarationTranslator, context());
|
NamespaceTranslator nestedNamespaceTranslator = new NamespaceTranslator(nestedNamespace, classDeclarationTranslator, context());
|
||||||
result.add(nestedNamespaceTranslator.getDeclarationAsInitializer());
|
result.add(nestedNamespaceTranslator.getDeclarationAsInitializer());
|
||||||
|
|
||||||
|
initializers.addAll(nestedNamespaceTranslator.getInitializers());
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -19,6 +19,7 @@ package org.jetbrains.k2js.translate.general;
|
|||||||
import com.google.dart.compiler.backend.js.JsNamer;
|
import com.google.dart.compiler.backend.js.JsNamer;
|
||||||
import com.google.dart.compiler.backend.js.JsPrettyNamer;
|
import com.google.dart.compiler.backend.js.JsPrettyNamer;
|
||||||
import com.google.dart.compiler.backend.js.ast.*;
|
import com.google.dart.compiler.backend.js.ast.*;
|
||||||
|
import com.google.dart.compiler.util.AstUtil;
|
||||||
import com.intellij.openapi.util.text.StringUtil;
|
import com.intellij.openapi.util.text.StringUtil;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.jet.lang.descriptors.ClassDescriptor;
|
import org.jetbrains.jet.lang.descriptors.ClassDescriptor;
|
||||||
@@ -28,7 +29,7 @@ import org.jetbrains.jet.lang.descriptors.NamespaceDescriptor;
|
|||||||
import org.jetbrains.jet.lang.psi.*;
|
import org.jetbrains.jet.lang.psi.*;
|
||||||
import org.jetbrains.jet.lang.resolve.BindingContext;
|
import org.jetbrains.jet.lang.resolve.BindingContext;
|
||||||
import org.jetbrains.jet.lang.types.lang.JetStandardLibrary;
|
import org.jetbrains.jet.lang.types.lang.JetStandardLibrary;
|
||||||
import org.jetbrains.k2js.config.EcmaVersion;
|
import org.jetbrains.k2js.config.Config;
|
||||||
import org.jetbrains.k2js.facade.MainCallParameters;
|
import org.jetbrains.k2js.facade.MainCallParameters;
|
||||||
import org.jetbrains.k2js.facade.exceptions.MainFunctionNotFoundException;
|
import org.jetbrains.k2js.facade.exceptions.MainFunctionNotFoundException;
|
||||||
import org.jetbrains.k2js.facade.exceptions.TranslationException;
|
import org.jetbrains.k2js.facade.exceptions.TranslationException;
|
||||||
@@ -148,10 +149,10 @@ public final class Translation {
|
|||||||
@NotNull
|
@NotNull
|
||||||
public static JsProgram generateAst(@NotNull BindingContext bindingContext,
|
public static JsProgram generateAst(@NotNull BindingContext bindingContext,
|
||||||
@NotNull List<JetFile> files, @NotNull MainCallParameters mainCallParameters,
|
@NotNull List<JetFile> files, @NotNull MainCallParameters mainCallParameters,
|
||||||
@NotNull EcmaVersion ecmaVersion, List<String> rawStatements)
|
@NotNull Config config, List<String> rawStatements)
|
||||||
throws TranslationException {
|
throws TranslationException {
|
||||||
try {
|
try {
|
||||||
return doGenerateAst(bindingContext, files, mainCallParameters, ecmaVersion, rawStatements);
|
return doGenerateAst(bindingContext, files, mainCallParameters, config, rawStatements);
|
||||||
}
|
}
|
||||||
catch (UnsupportedOperationException e) {
|
catch (UnsupportedOperationException e) {
|
||||||
throw new UnsupportedFeatureException("Unsupported feature used.", e);
|
throw new UnsupportedFeatureException("Unsupported feature used.", e);
|
||||||
@@ -164,10 +165,10 @@ public final class Translation {
|
|||||||
@NotNull
|
@NotNull
|
||||||
private static JsProgram doGenerateAst(@NotNull BindingContext bindingContext, @NotNull List<JetFile> files,
|
private static JsProgram doGenerateAst(@NotNull BindingContext bindingContext, @NotNull List<JetFile> files,
|
||||||
@NotNull MainCallParameters mainCallParameters,
|
@NotNull MainCallParameters mainCallParameters,
|
||||||
@NotNull EcmaVersion ecmaVersion, List<String> rawStatements) throws MainFunctionNotFoundException {
|
@NotNull Config config, List<String> rawStatements) throws MainFunctionNotFoundException {
|
||||||
//TODO: move some of the code somewhere
|
//TODO: move some of the code somewhere
|
||||||
JetStandardLibrary standardLibrary = JetStandardLibrary.getInstance();
|
JetStandardLibrary standardLibrary = JetStandardLibrary.getInstance();
|
||||||
StaticContext staticContext = StaticContext.generateStaticContext(standardLibrary, bindingContext, ecmaVersion);
|
StaticContext staticContext = StaticContext.generateStaticContext(standardLibrary, bindingContext, config.getTarget());
|
||||||
JsProgram program = staticContext.getProgram();
|
JsProgram program = staticContext.getProgram();
|
||||||
JsBlock block = program.getGlobalBlock();
|
JsBlock block = program.getGlobalBlock();
|
||||||
|
|
||||||
@@ -177,6 +178,8 @@ public final class Translation {
|
|||||||
|
|
||||||
TranslationContext context = TranslationContext.rootContext(staticContext);
|
TranslationContext context = TranslationContext.rootContext(staticContext);
|
||||||
statements.addAll(translateFiles(files, context));
|
statements.addAll(translateFiles(files, context));
|
||||||
|
defineModule(statements, context, config);
|
||||||
|
|
||||||
if (mainCallParameters.shouldBeGenerated()) {
|
if (mainCallParameters.shouldBeGenerated()) {
|
||||||
statements.add(generateCallToMain(context, files, mainCallParameters.arguments()));
|
statements.add(generateCallToMain(context, files, mainCallParameters.arguments()));
|
||||||
}
|
}
|
||||||
@@ -186,6 +189,14 @@ public final class Translation {
|
|||||||
return context.program();
|
return context.program();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static void defineModule(@NotNull List<JsStatement> statements,
|
||||||
|
@NotNull TranslationContext context,
|
||||||
|
@NotNull Config config) {
|
||||||
|
statements.add(AstUtil.newInvocation(context.namer().kotlin("defineModule"),
|
||||||
|
context.program().getStringLiteral(config.getModuleId()),
|
||||||
|
context.jsScope().declareName("_").makeRef()).makeStmt());
|
||||||
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private static JsStatement generateCallToMain(@NotNull TranslationContext context, @NotNull List<JetFile> files,
|
private static JsStatement generateCallToMain(@NotNull TranslationContext context, @NotNull List<JetFile> files,
|
||||||
@NotNull List<String> arguments) throws MainFunctionNotFoundException {
|
@NotNull List<String> arguments) throws MainFunctionNotFoundException {
|
||||||
@@ -214,12 +225,12 @@ public final class Translation {
|
|||||||
JsAstUtils.setArguments(translatedCall, Collections.<JsExpression>singletonList(arrayLiteral));
|
JsAstUtils.setArguments(translatedCall, Collections.<JsExpression>singletonList(arrayLiteral));
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
|
||||||
private static void generateTestCalls(@NotNull TranslationContext context,
|
private static void generateTestCalls(@NotNull TranslationContext context,
|
||||||
@NotNull List<JetFile> files,
|
@NotNull List<JetFile> files,
|
||||||
@NotNull JsBlock block,
|
@NotNull JsBlock block,
|
||||||
List<String> rawStatements) {
|
List<String> rawStatements) {
|
||||||
ClassDescriptor lastClassDescriptor = null;
|
ClassDescriptor lastClassDescriptor = null;
|
||||||
|
boolean declaredVar = false;
|
||||||
List<JetNamedFunction> functions = JetTestFunctionDetector.findTestFunctions(context.bindingContext(), files);
|
List<JetNamedFunction> functions = JetTestFunctionDetector.findTestFunctions(context.bindingContext(), files);
|
||||||
for (JetNamedFunction function : functions) {
|
for (JetNamedFunction function : functions) {
|
||||||
FunctionDescriptor functionDescriptor = getFunctionDescriptor(context.bindingContext(), function);
|
FunctionDescriptor functionDescriptor = getFunctionDescriptor(context.bindingContext(), function);
|
||||||
@@ -228,9 +239,16 @@ public final class Translation {
|
|||||||
if (containingDeclaration instanceof ClassDescriptor) {
|
if (containingDeclaration instanceof ClassDescriptor) {
|
||||||
ClassDescriptor classDescriptor = (ClassDescriptor) containingDeclaration;
|
ClassDescriptor classDescriptor = (ClassDescriptor) containingDeclaration;
|
||||||
String className = getQualifiedName(classDescriptor);
|
String className = getQualifiedName(classDescriptor);
|
||||||
|
if (lastClassDescriptor != classDescriptor) {
|
||||||
|
lastClassDescriptor = classDescriptor;
|
||||||
|
String prefix = "";
|
||||||
|
if (!declaredVar) {
|
||||||
|
prefix = "var ";
|
||||||
|
declaredVar = true;
|
||||||
|
}
|
||||||
|
rawStatements.add(prefix + "_testCase = new Kotlin.main." + className + "();");
|
||||||
|
}
|
||||||
rawStatements.add("QUnit.test( \"" + className + "." + funName + "()\" , function() {");
|
rawStatements.add("QUnit.test( \"" + className + "." + funName + "()\" , function() {");
|
||||||
String prefix = " var ";
|
|
||||||
rawStatements.add(prefix + "_testCase = new Kotlin.defs." + className + "();");
|
|
||||||
//rawStatements.add(" expect(0);");
|
//rawStatements.add(" expect(0);");
|
||||||
rawStatements.add(" _testCase." + funName + "();");
|
rawStatements.add(" _testCase." + funName + "();");
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
@@ -213,7 +213,7 @@ public final class CallTranslator extends AbstractTranslator {
|
|||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private JsInvocation generateCallMethodInvocation() {
|
private JsInvocation generateCallMethodInvocation() {
|
||||||
JsNameRef callMethodNameRef = AstUtil.newQualifiedNameRef("call");
|
JsNameRef callMethodNameRef = new JsNameRef("call");
|
||||||
JsInvocation callMethodInvocation = new JsInvocation();
|
JsInvocation callMethodInvocation = new JsInvocation();
|
||||||
callMethodInvocation.setQualifier(callMethodNameRef);
|
callMethodInvocation.setQualifier(callMethodNameRef);
|
||||||
setQualifier(callMethodInvocation, callParameters.getFunctionReference());
|
setQualifier(callMethodInvocation, callParameters.getFunctionReference());
|
||||||
|
|||||||
@@ -16,8 +16,8 @@
|
|||||||
|
|
||||||
package org.jetbrains.k2js.translate.utils;
|
package org.jetbrains.k2js.translate.utils;
|
||||||
|
|
||||||
import com.google.common.collect.Sets;
|
|
||||||
import com.intellij.psi.PsiElement;
|
import com.intellij.psi.PsiElement;
|
||||||
|
import com.intellij.util.containers.OrderedSet;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
import org.jetbrains.jet.lang.descriptors.*;
|
import org.jetbrains.jet.lang.descriptors.*;
|
||||||
@@ -321,7 +321,7 @@ public final class BindingUtils {
|
|||||||
@NotNull
|
@NotNull
|
||||||
public static Set<NamespaceDescriptor> getAllNonNativeNamespaceDescriptors(@NotNull BindingContext context,
|
public static Set<NamespaceDescriptor> getAllNonNativeNamespaceDescriptors(@NotNull BindingContext context,
|
||||||
@NotNull List<JetFile> files) {
|
@NotNull List<JetFile> files) {
|
||||||
Set<NamespaceDescriptor> descriptorSet = Sets.newHashSet();
|
Set<NamespaceDescriptor> descriptorSet = new OrderedSet<NamespaceDescriptor>();
|
||||||
for (JetFile file : files) {
|
for (JetFile file : files) {
|
||||||
//TODO: can't be
|
//TODO: can't be
|
||||||
NamespaceDescriptor namespaceDescriptor = getNamespaceDescriptor(context, file);
|
NamespaceDescriptor namespaceDescriptor = getNamespaceDescriptor(context, file);
|
||||||
|
|||||||
@@ -33,11 +33,13 @@ import java.util.*;
|
|||||||
*/
|
*/
|
||||||
public final class JsAstUtils {
|
public final class JsAstUtils {
|
||||||
private static final JsNameRef DEFINE_PROPERTY = new JsNameRef("defineProperty");
|
private static final JsNameRef DEFINE_PROPERTY = new JsNameRef("defineProperty");
|
||||||
|
public static final JsNameRef CREATE_OBJECT = new JsNameRef("create");
|
||||||
private static final JsNameRef EMPTY_REF = new JsNameRef("");
|
private static final JsNameRef EMPTY_REF = new JsNameRef("");
|
||||||
|
|
||||||
static {
|
static {
|
||||||
JsNameRef globalObjectReference = new JsNameRef("Object");
|
JsNameRef globalObjectReference = new JsNameRef("Object");
|
||||||
DEFINE_PROPERTY.setQualifier(globalObjectReference);
|
DEFINE_PROPERTY.setQualifier(globalObjectReference);
|
||||||
|
CREATE_OBJECT.setQualifier(globalObjectReference);
|
||||||
}
|
}
|
||||||
|
|
||||||
private JsAstUtils() {
|
private JsAstUtils() {
|
||||||
@@ -301,21 +303,26 @@ public final class JsAstUtils {
|
|||||||
return createPropertyDataDescriptor(descriptor.getModality().isOverridable(), descriptor, value, context);
|
return createPropertyDataDescriptor(descriptor.getModality().isOverridable(), descriptor, value, context);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
public static JsObjectLiteral createDataDescriptor(@NotNull JsExpression value, boolean writable, @NotNull TranslationContext context) {
|
||||||
|
JsObjectLiteral dataDescriptor = new JsObjectLiteral();
|
||||||
|
dataDescriptor.getPropertyInitializers().add(new JsPropertyInitializer(context.program().getStringLiteral("value"), value));
|
||||||
|
if (writable) {
|
||||||
|
dataDescriptor.getPropertyInitializers().add(context.namer().writablePropertyDescriptorField());
|
||||||
|
}
|
||||||
|
return dataDescriptor;
|
||||||
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private static JsObjectLiteral createPropertyDataDescriptor(boolean writable,
|
private static JsObjectLiteral createPropertyDataDescriptor(boolean writable,
|
||||||
@NotNull DeclarationDescriptor descriptor,
|
@NotNull DeclarationDescriptor descriptor,
|
||||||
@NotNull JsExpression value,
|
@NotNull JsExpression value,
|
||||||
@NotNull TranslationContext context) {
|
@NotNull TranslationContext context) {
|
||||||
JsObjectLiteral jsPropertyDescriptor = new JsObjectLiteral();
|
JsObjectLiteral dataDescriptor = createDataDescriptor(value, writable, context);
|
||||||
List<JsPropertyInitializer> meta = jsPropertyDescriptor.getPropertyInitializers();
|
|
||||||
meta.add(new JsPropertyInitializer(context.program().getStringLiteral("value"), value));
|
|
||||||
if (writable) {
|
|
||||||
meta.add(context.namer().writablePropertyDescriptorField());
|
|
||||||
}
|
|
||||||
if (AnnotationsUtils.isEnumerable(descriptor)) {
|
if (AnnotationsUtils.isEnumerable(descriptor)) {
|
||||||
meta.add(context.namer().enumerablePropertyDescriptorField());
|
dataDescriptor.getPropertyInitializers().add(context.namer().enumerablePropertyDescriptorField());
|
||||||
}
|
}
|
||||||
return jsPropertyDescriptor;
|
return dataDescriptor;
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
|
|||||||
@@ -30,7 +30,6 @@ import org.jetbrains.jet.lang.resolve.scopes.receivers.ReceiverDescriptor;
|
|||||||
import org.jetbrains.jet.lang.types.JetType;
|
import org.jetbrains.jet.lang.types.JetType;
|
||||||
import org.jetbrains.jet.lang.types.expressions.OperatorConventions;
|
import org.jetbrains.jet.lang.types.expressions.OperatorConventions;
|
||||||
import org.jetbrains.k2js.config.LibrarySourcesConfig;
|
import org.jetbrains.k2js.config.LibrarySourcesConfig;
|
||||||
import org.jetbrains.k2js.translate.context.Namer;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
@@ -145,16 +144,6 @@ public final class JsDescriptorUtils {
|
|||||||
return (functionDescriptor.getReceiverParameter().exists());
|
return (functionDescriptor.getReceiverParameter().exists());
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
|
||||||
public static String getNameForNamespace(@NotNull NamespaceDescriptor descriptor) {
|
|
||||||
if (descriptor.getContainingDeclaration() instanceof ModuleDescriptor) {
|
|
||||||
return Namer.getRootNamespaceName();
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
return descriptor.getName().getName();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//TODO: why callable descriptor
|
//TODO: why callable descriptor
|
||||||
@Nullable
|
@Nullable
|
||||||
public static DeclarationDescriptor getExpectedThisDescriptor(@NotNull CallableDescriptor callableDescriptor) {
|
public static DeclarationDescriptor getExpectedThisDescriptor(@NotNull CallableDescriptor callableDescriptor) {
|
||||||
@@ -239,13 +228,18 @@ public final class JsDescriptorUtils {
|
|||||||
List<DeclarationDescriptor> result = Lists.newArrayList();
|
List<DeclarationDescriptor> result = Lists.newArrayList();
|
||||||
for (DeclarationDescriptor descriptor : namespace.getMemberScope().getAllDescriptors()) {
|
for (DeclarationDescriptor descriptor : namespace.getMemberScope().getAllDescriptors()) {
|
||||||
if (!AnnotationsUtils.isPredefinedObject(descriptor)) {
|
if (!AnnotationsUtils.isPredefinedObject(descriptor)) {
|
||||||
PsiElement psiElement = BindingContextUtils.descriptorToDeclaration(context, descriptor);
|
// namespace may be defined in multiple files
|
||||||
if (psiElement != null) {
|
if (!(descriptor instanceof NamespaceDescriptor)) {
|
||||||
PsiFile file = psiElement.getContainingFile();
|
PsiElement psiElement = BindingContextUtils.descriptorToDeclaration(context, descriptor);
|
||||||
if (file.getUserData(LibrarySourcesConfig.EXTERNAL_LIB) == null) {
|
if (psiElement != null) {
|
||||||
result.add(descriptor);
|
PsiFile file = psiElement.getContainingFile();
|
||||||
|
if (file.getUserData(LibrarySourcesConfig.EXTERNAL_MODULE_NAME) != null) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
result.add(descriptor);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
|
|||||||
@@ -23,7 +23,6 @@ import org.jetbrains.annotations.Nullable;
|
|||||||
import org.jetbrains.jet.lang.psi.*;
|
import org.jetbrains.jet.lang.psi.*;
|
||||||
import org.jetbrains.jet.lexer.JetToken;
|
import org.jetbrains.jet.lexer.JetToken;
|
||||||
import org.jetbrains.jet.lexer.JetTokens;
|
import org.jetbrains.jet.lexer.JetTokens;
|
||||||
import org.jetbrains.k2js.translate.context.Namer;
|
|
||||||
|
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
@@ -143,17 +142,6 @@ public final class PsiUtils {
|
|||||||
return nameAsDeclaration;
|
return nameAsDeclaration;
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
|
||||||
public static String getNamespaceName(@NotNull JetFile psiFile) {
|
|
||||||
JetNamespaceHeader namespaceHeader = psiFile.getNamespaceHeader();
|
|
||||||
String name = namespaceHeader.getName();
|
|
||||||
assert name != null : "NamespaceHeader must have a name";
|
|
||||||
if (name.isEmpty()) {
|
|
||||||
return Namer.getRootNamespaceName();
|
|
||||||
}
|
|
||||||
return name;
|
|
||||||
}
|
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static JetExpression getLoopRange(@NotNull JetForExpression expression) {
|
public static JetExpression getLoopRange(@NotNull JetForExpression expression) {
|
||||||
JetExpression rangeExpression = expression.getLoopRange();
|
JetExpression rangeExpression = expression.getLoopRange();
|
||||||
|
|||||||
@@ -43,7 +43,7 @@ import static org.jetbrains.k2js.translate.utils.JsDescriptorUtils.getExpectedRe
|
|||||||
*/
|
*/
|
||||||
public final class TranslationUtils {
|
public final class TranslationUtils {
|
||||||
|
|
||||||
private static JsNameRef UNDEFINED_LITERAL = AstUtil.newQualifiedNameRef("undefined");
|
private static final JsNameRef UNDEFINED_LITERAL = AstUtil.newQualifiedNameRef("undefined");
|
||||||
|
|
||||||
private TranslationUtils() {
|
private TranslationUtils() {
|
||||||
}
|
}
|
||||||
@@ -64,11 +64,7 @@ public final class TranslationUtils {
|
|||||||
@NotNull
|
@NotNull
|
||||||
private static JsPropertyInitializer translateExtensionFunctionAsEcma5PropertyDescriptor(@NotNull JsFunction function,
|
private static JsPropertyInitializer translateExtensionFunctionAsEcma5PropertyDescriptor(@NotNull JsFunction function,
|
||||||
@NotNull FunctionDescriptor descriptor, @NotNull TranslationContext context) {
|
@NotNull FunctionDescriptor descriptor, @NotNull TranslationContext context) {
|
||||||
JsObjectLiteral meta = new JsObjectLiteral();
|
JsObjectLiteral meta = JsAstUtils.createDataDescriptor(function, descriptor.getModality().isOverridable(), context);
|
||||||
meta.getPropertyInitializers().add(new JsPropertyInitializer(context.program().getStringLiteral("value"), function));
|
|
||||||
if (descriptor.getModality().isOverridable()) {
|
|
||||||
meta.getPropertyInitializers().add(context.namer().writablePropertyDescriptorField());
|
|
||||||
}
|
|
||||||
return new JsPropertyInitializer(context.getNameForDescriptor(descriptor).makeRef(), meta);
|
return new JsPropertyInitializer(context.getNameForDescriptor(descriptor).makeRef(), meta);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -14,9 +14,7 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
foo = Kotlin.createNamespace({initialize:function(){
|
foo = Kotlin.definePackage({box:function(){
|
||||||
}
|
|
||||||
, box:function(){
|
|
||||||
return !false;
|
return !false;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -46,9 +46,7 @@
|
|||||||
return {A:A, B:B, C:C};
|
return {A:A, B:B, C:C};
|
||||||
}
|
}
|
||||||
();
|
();
|
||||||
foo = Kotlin.createNamespace(classes, {initialize:function(){
|
foo = Kotlin.definePackage(classes, {box:function(){
|
||||||
}
|
|
||||||
, box:function(){
|
|
||||||
return (new foo.C).get_order() === 'ABC' && (new foo.B).get_order() === 'AB' && (new foo.A).get_order() === 'A';
|
return (new foo.C).get_order() === 'ABC' && (new foo.B).get_order() === 'AB' && (new foo.A).get_order() === 'A';
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -31,7 +31,7 @@ var kotlin = {set:function (receiver, key, value) {
|
|||||||
return (obj1 === obj2);
|
return (obj1 === obj2);
|
||||||
};
|
};
|
||||||
|
|
||||||
Kotlin.defs = {};
|
Kotlin.modules = {};
|
||||||
Kotlin.Exceptions = {};
|
Kotlin.Exceptions = {};
|
||||||
Kotlin.Exception = Kotlin.$createClass();
|
Kotlin.Exception = Kotlin.$createClass();
|
||||||
Kotlin.RuntimeException = Kotlin.$createClass(Kotlin.Exception);
|
Kotlin.RuntimeException = Kotlin.$createClass(Kotlin.Exception);
|
||||||
@@ -44,7 +44,7 @@ var kotlin = {set:function (receiver, key, value) {
|
|||||||
Kotlin.Exceptions.UnsupportedOperationException = Kotlin.$createClass(Kotlin.Exception);
|
Kotlin.Exceptions.UnsupportedOperationException = Kotlin.$createClass(Kotlin.Exception);
|
||||||
Kotlin.Exceptions.IOException = Kotlin.$createClass(Kotlin.Exception);
|
Kotlin.Exceptions.IOException = Kotlin.$createClass(Kotlin.Exception);
|
||||||
|
|
||||||
Kotlin.throwNPE = function() {
|
Kotlin.throwNPE = function () {
|
||||||
throw Kotlin.$new(Kotlin.Exceptions.NullPointerException)();
|
throw Kotlin.$new(Kotlin.Exceptions.NullPointerException)();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -141,9 +141,7 @@ var Kotlin = {};
|
|||||||
}
|
}
|
||||||
})();
|
})();
|
||||||
|
|
||||||
Kotlin.createNamespace = function () {
|
Kotlin.definePackage = Kotlin.createTrait;
|
||||||
return Kotlin.createTrait.apply(null, arguments);
|
|
||||||
};
|
|
||||||
|
|
||||||
Kotlin.createClass = (function () {
|
Kotlin.createClass = (function () {
|
||||||
var METHODS = {addMethods: addMethods};
|
var METHODS = {addMethods: addMethods};
|
||||||
@@ -243,4 +241,12 @@ var Kotlin = {};
|
|||||||
var singletonClass = Kotlin.createClass.apply(null, arguments);
|
var singletonClass = Kotlin.createClass.apply(null, arguments);
|
||||||
return new singletonClass();
|
return new singletonClass();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
Kotlin.defineModule = function (id, module) {
|
||||||
|
if (id in Kotlin.modules) {
|
||||||
|
throw Kotlin.$new(Kotlin.Exceptions.IllegalArgumentException)();
|
||||||
|
}
|
||||||
|
|
||||||
|
Kotlin.modules[id] = module;
|
||||||
|
};
|
||||||
})();
|
})();
|
||||||
|
|||||||
@@ -110,18 +110,27 @@ var Kotlin = {};
|
|||||||
return o;
|
return o;
|
||||||
};
|
};
|
||||||
|
|
||||||
function emptyFunction() {
|
|
||||||
}
|
|
||||||
|
|
||||||
Kotlin.createNamespace = function (initializer, properties, classesAndNestedNamespaces) {
|
Kotlin.definePackage = function (functionsAndClasses, nestedNamespaces) {
|
||||||
var o = Object.create(null, properties || undefined);
|
//var p = parent[localName];
|
||||||
Object.defineProperty(o, "initialize", {value: initializer || emptyFunction});
|
//if (!p) {
|
||||||
var keys = Object.keys(classesAndNestedNamespaces);
|
// p = Object.create(null, functionsAndClasses || undefined);
|
||||||
for (var i = 0, n = keys.length; i < n; i++) {
|
// Object.defineProperty(parent, localName, {value: p});
|
||||||
var name = keys[i];
|
//}
|
||||||
Object.defineProperty(o, name, {value: classesAndNestedNamespaces[name]});
|
//else if (functionsAndClasses) {
|
||||||
|
// Object.defineProperties(p, functionsAndClasses);
|
||||||
|
//}
|
||||||
|
var p = Object.create(null, functionsAndClasses || undefined);
|
||||||
|
|
||||||
|
if (nestedNamespaces) {
|
||||||
|
var keys = Object.keys(nestedNamespaces);
|
||||||
|
for (var i = 0, n = keys.length; i < n; i++) {
|
||||||
|
var name = keys[i];
|
||||||
|
Object.defineProperty(p, name, {value:nestedNamespaces[name]});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
return o;
|
|
||||||
|
return p;
|
||||||
};
|
};
|
||||||
|
|
||||||
Kotlin.$new = function (f) {
|
Kotlin.$new = function (f) {
|
||||||
@@ -170,4 +179,13 @@ var Kotlin = {};
|
|||||||
|
|
||||||
return Kotlin.createClass(parent || null, initializer, descriptors);
|
return Kotlin.createClass(parent || null, initializer, descriptors);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
Kotlin.defineModule = function (id, module) {
|
||||||
|
if (id in Kotlin.modules) {
|
||||||
|
throw Kotlin.$new(Kotlin.Exceptions.IllegalArgumentException)();
|
||||||
|
}
|
||||||
|
|
||||||
|
Object.freeze(module);
|
||||||
|
Object.defineProperty(Kotlin.modules, id, {value: module});
|
||||||
|
};
|
||||||
})();
|
})();
|
||||||
|
|||||||
Reference in New Issue
Block a user