awaitLet allow synchronous bindings. Close #68
This commit is contained in:
@@ -699,48 +699,60 @@ class Macros {
|
|||||||
macros["assertLet"] = ifLet.bind(true);
|
macros["assertLet"] = ifLet.bind(true);
|
||||||
|
|
||||||
k.doc("awaitLet", 2, null, "(awaitLet [<promise bindings...>] <?catchHandler> <body...>)");
|
k.doc("awaitLet", 2, null, "(awaitLet [<promise bindings...>] <?catchHandler> <body...>)");
|
||||||
function awaitLet(wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) {
|
function awaitLet(rejectionHandler:ReaderExp->ReaderExp, wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) {
|
||||||
|
|
||||||
var bindingList = exps[0].bindingList("awaitLet");
|
var bindingList = exps[0].bindingList("awaitLet");
|
||||||
var firstName = bindingList.shift();
|
var firstName = bindingList.shift();
|
||||||
var firstValue = bindingList.shift();
|
var firstValue = bindingList.shift();
|
||||||
var b = wholeExp.expBuilder();
|
var b = wholeExp.expBuilder();
|
||||||
|
|
||||||
var firstNameStr = firstName.symbolNameValue();
|
if (rejectionHandler == null) {
|
||||||
var error = b.callSymbol("+", [b.str('awaitLet $firstNameStr rejected promise: '), b.symbol("reason")]);
|
function error(firstName:ReaderExp) {
|
||||||
var rejectionHandler = switch (exps[1].def) {
|
return b.callSymbol("+", [b.str('awaitLet ${firstName.symbolNameValue()} rejected promise: '), b.symbol("reason")]);
|
||||||
case CallExp({pos: _, def: Symbol("catch")}, args):
|
}
|
||||||
exps.splice(1,1);
|
rejectionHandler = switch (exps[1].def) {
|
||||||
b.callSymbol("lambda", args);
|
case CallExp({pos: _, def: Symbol("catch")}, args):
|
||||||
|
exps.splice(1,1);
|
||||||
|
(exp) -> b.callSymbol("lambda", args);
|
||||||
|
default:
|
||||||
|
(firstName) -> b.callSymbol("lambda", [
|
||||||
|
b.list([b.symbol("reason")]),
|
||||||
|
b.callSymbol("#when", [
|
||||||
|
b.symbol("vscode"),
|
||||||
|
b.callSymbol("Vscode.window.showErrorMessage", [error(firstName)]),
|
||||||
|
]),
|
||||||
|
// If running VSCode js, this throw will be a no-op but it makes the expression type-unify:
|
||||||
|
b.callSymbol("throw", [
|
||||||
|
error(firstName)
|
||||||
|
])
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
var innerExp = if (bindingList.length == 0) {
|
||||||
|
b.begin(exps.slice(1));
|
||||||
|
} else {
|
||||||
|
awaitLet(rejectionHandler, wholeExp, [b.list(bindingList)].concat(exps.slice(1)), k);
|
||||||
|
};
|
||||||
|
switch(firstName.def) {
|
||||||
|
case MetaExp("sync", firstName):
|
||||||
|
return b.let([firstName, firstValue], [innerExp]);
|
||||||
|
case MetaExp(other, _):
|
||||||
|
throw KissError.fromExp(firstName, 'bad meta annotation &$other');
|
||||||
default:
|
default:
|
||||||
b.callSymbol("lambda", [
|
|
||||||
b.list([b.symbol("reason")]),
|
|
||||||
b.callSymbol("#when", [
|
|
||||||
b.symbol("vscode"),
|
|
||||||
b.callSymbol("Vscode.window.showErrorMessage", [error]),
|
|
||||||
]),
|
|
||||||
// If running VSCode js, this throw will be a no-op but it makes the expression type-unify:
|
|
||||||
b.callSymbol("throw", [
|
|
||||||
error
|
|
||||||
])
|
|
||||||
]);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return b.call(b.field("then", firstValue), [
|
return b.call(b.field("then", firstValue), [
|
||||||
b.callSymbol("lambda", [
|
b.callSymbol("lambda", [
|
||||||
b.list([firstName]),
|
b.list([firstName]),
|
||||||
if (bindingList.length == 0) {
|
innerExp
|
||||||
b.begin(exps.slice(1));
|
|
||||||
} else {
|
|
||||||
awaitLet(wholeExp, [b.list(bindingList)].concat(exps.slice(1)), k);
|
|
||||||
}
|
|
||||||
]),
|
]),
|
||||||
// Handle rejections:
|
// Handle rejections:
|
||||||
rejectionHandler
|
rejectionHandler(firstName)
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
macros["awaitLet"] = awaitLet;
|
macros["awaitLet"] = awaitLet.bind(null);
|
||||||
|
|
||||||
k.doc("whileLet", 2, null, "(whileLet [<bindings...>] <body...>)");
|
k.doc("whileLet", 2, null, "(whileLet [<bindings...>] <body...>)");
|
||||||
macros["whileLet"] = (wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) -> {
|
macros["whileLet"] = (wholeExp:ReaderExp, exps:Array<ReaderExp>, k:KissState) -> {
|
||||||
|
@@ -52,22 +52,22 @@ class ${className} {}
|
|||||||
(showTextDocument (Uri.file (correspondingFile .fileName .document activeTextEditor))))
|
(showTextDocument (Uri.file (correspondingFile .fileName .document activeTextEditor))))
|
||||||
|
|
||||||
(function insertUTestCase [&opt _]
|
(function insertUTestCase [&opt _]
|
||||||
(awaitLet [testName (inputBox)]
|
(awaitLet [testName (inputBox)
|
||||||
(let [testName
|
&sync testName
|
||||||
"$(.toUpperCase (testName.substr 0 1))$(testName.substr 1)"]
|
"$(.toUpperCase (testName.substr 0 1))$(testName.substr 1)"
|
||||||
(awaitLet [_ (insert
|
_ (insert
|
||||||
"function test${testName}() {
|
"function test${testName}() {
|
||||||
_test${testName}();
|
_test${testName}();
|
||||||
}
|
}
|
||||||
")
|
")
|
||||||
_ (showTextDocument (Uri.file (correspondingFile .fileName .document activeTextEditor)))]
|
_ (showTextDocument (Uri.file (correspondingFile .fileName .document activeTextEditor)))
|
||||||
(let [pos (activeTextEditor.document.positionAt .length (activeTextEditor.document.getText))]
|
&sync pos (activeTextEditor.document.positionAt .length (activeTextEditor.document.getText))
|
||||||
(awaitLet [_ (insertAt pos
|
_ (insertAt pos
|
||||||
"
|
"
|
||||||
|
|
||||||
(function _test${testName} []
|
(function _test${testName} []
|
||||||
(Assert.pass))
|
(Assert.pass))
|
||||||
")]
|
")
|
||||||
(let [endPos (activeTextEditor.document.positionAt .length (activeTextEditor.document.getText))]
|
&sync endPos (activeTextEditor.document.positionAt .length (activeTextEditor.document.getText))]
|
||||||
(activeTextEditor.revealRange (new Range pos endPos))
|
(activeTextEditor.revealRange (new Range pos endPos))
|
||||||
(set activeTextEditor.selection (new Selection pos endPos)))))))))
|
(set activeTextEditor.selection (new Selection pos endPos))))
|
Reference in New Issue
Block a user