执行javascript脚本并等待promise被解析以返回值
我想运行一个脚本,等待承诺返回值执行javascript脚本并等待promise被解析以返回值,javascript,php,laravel,selenium,laravel-dusk,Javascript,Php,Laravel,Selenium,Laravel Dusk,我想运行一个脚本,等待承诺返回值 $dusk->script('return //something'); 我想要运行的javascript函数是一个承诺 fetch(url).then(r => r.blob()).then(blob => { var reader = new FileReader(); reader.onload = function() { var b64 = reader.result.replace(/^data:.
$dusk->script('return //something');
我想要运行的javascript函数是一个承诺
fetch(url).then(r => r.blob()).then(blob => {
var reader = new FileReader();
reader.onload = function() {
var b64 = reader.result.replace(/^data:.+;base64,/, '');
console.log(b64); // I want to return this value
};
reader.readAsDataURL(blob);
});
我想返回b64
变量,但这不会发生
$b64 = $dusk->script("
var b64;
fetch(url).then(r => r.blob()).then(blob => {
var reader = new FileReader();
reader.onload = function() {
b64 = reader.result.replace(/^data:.+;base64,/, '');
};
reader.readAsDataURL(blob);
});
// When `b64` is ready, I want to return it
return b64;
");
这是一种可能性。我认为它也适用于黄昏/硒。 线索是onload函数基本上是一个回调函数,因此我们希望使用该回调函数来解析承诺。 如果您想要同步外观的代码,async/await也可以为您这样做,但最终结果是一样的,会返回一个承诺,这样您就可以继续承诺链
fetch(url)
.then(r => r.blob())
.then(blob => new Promise(( resolve ) => {
var reader = new FileReader();
reader.onload = function() {
var b64 = reader.result.replace(/^data:.+;base64,/, '');
resolve( b64 );
};
reader.readAsDataURL(blob);
})
.then( b64 => {
// do something with b64
});
这确实意味着您不能将其返回到外部$b64=
编辑:
所以不是
$b64 = fetch(url)
.then( response => ... )
.then( blob => ... )
.then( image => ... );
renderImage( $b64 );
你想做什么
fetch(url)
.then( response => ... )
.then( blob => ... )
.then( image => ... )
.then( renderImage );
或:
编辑2:
$dusk->script('
var url = document.getElementById("img_file").getAttribute("src");
fetch(url)
.then(r => r.blob())
.then(blob => new Promise(( resolve ) => {
var reader = new FileReader();
reader.onload = function() {
var b64 = reader.result.replace(/^data:.+;base64,/, "");
resolve( b64 );
};
reader.readAsDataURL(blob);
}))
.then( b64 => {
$("body").append(`<input id="b64string" value="${b64}">`);
});
');
// wait until ajax to be finished
$dusk->waitUntil("!$.active", 30);
$b64Img = $dusk->script("return document.getElementById('b64string').value;"); // this returns array
dd($b64Img[0]); // works!
不要等待实际的承诺,等待承诺的结果显示在屏幕上,因此根据Dash文档,在Dash抛出错误之前,您给承诺5秒钟的时间来解决
如果Promise将在页面上呈现结果,请尝试检测图像将呈现到的图像标记中的更改
$dusk->script("
fetch(url).then(r => r.blob()).then(blob => {
var reader = new FileReader();
reader.onload = function() {
var b64 = reader.result.replace(/^data:.+;base64,/, '');
document.querySelector( 'body' ).classList.add( 'loaded_image' );
};
reader.readAsDataURL(blob);
});
");
$dusk->waitUntil('body.loaded_image');
解决方案:
$dusk->script('
var url = document.getElementById("img_file").getAttribute("src");
fetch(url)
.then(r => r.blob())
.then(blob => new Promise(( resolve ) => {
var reader = new FileReader();
reader.onload = function() {
var b64 = reader.result.replace(/^data:.+;base64,/, "");
resolve( b64 );
};
reader.readAsDataURL(blob);
}))
.then( b64 => {
$("body").append(`<input id="b64string" value="${b64}">`);
});
');
// wait until ajax to be finished
$dusk->waitUntil("!$.active", 30);
$b64Img = $dusk->script("return document.getElementById('b64string').value;"); // this returns array
dd($b64Img[0]); // works!
$dash->script('
var url=document.getElementById(“img_文件”).getAttribute(“src”);
获取(url)
.then(r=>r.blob())
.然后(blob=>新承诺((解决)=>{
var reader=new FileReader();
reader.onload=函数(){
var b64=reader.result.replace(/^data:.+;base64,/,“”);
决议(b64);
};
reader.readAsDataURL(blob);
}))
。然后(b64=>{
$(“正文”)。追加(``);
});
');
//等待ajax完成
$黄昏->等待直到(!$.active),30);
$b64Img=$dusk->script(“return document.getElementById('b64string').value;”);//这将返回一个数组
dd($b64Img[0]);//作品
的可能副本,因此基本上您希望将reader.onload()包装在另一个承诺中并返回该承诺。然后onload()可以解决这个问题。所以你可以用另一个继续这个promsie链。然后()我想不出来,这就是我问的原因。如何将reader.onload=function(){}
包装到另一个承诺中?如果我最后写了return b64(在最后一个then()
)之后),它不就是返回undefined吗?我不需要返回最后一个then()
?这就是问题所在,除非使用异步/等待语法,否则无法返回到外部变量。您需要在处理程序中使用$b64执行任何操作。然后()
处理程序。最简单的方法就是将一个函数传递给。然后()
,它将执行您想用$b64=..
执行的任何操作。或者使用async/await语法重写它,这样返回就可以像writetten一样工作。也许黄昏也有一些语法糖,让我们先解包,然后再解析结果。这就是我感到困惑的地方。异步/等待语法是什么意思?我很困惑如何做到这一点。我看了看黄昏,但——所以我以后也无法接近它;因此,需要在$dash->script()
中执行此操作。哦,您的意思是,在最后一个then()
中,调用另一个将返回b64变量的函数-让我尝试一下,如果混淆,我不会使用它。最终,async/await只是编写承诺的语法糖。