Downloading PDFs opened in new tab with CasperJS - phantomjs

I'm trying to write a casperJS program that can navigate and download PDFs. If I can grab an actual URL corresponding to the PDF it's pretty straight-forward, but that isn't always the case. To test this, I've been working with this simple example locally:
<html>
<head>
</head>
<body>
<h1 class="page-title">Hello</h1>
<a id='1' href="test.pdf" target="_blank">one</a>
</body>
</html>
Basic casper:
casper.start('file:///opt/templates/templates/src/main/resources/casperjs/example.html').then(function() {
this.echo('started')
});
casper.then(function() {
this.waitForSelector('a', function() {
this.click('a');
});
});
casper.wait(1000, function() {
this.echo(JSON.stringify(this.popups[0]));
});
casper.run();
When I run this, the (only) popup that's present is a blank HTML page that never loads. It's also worth noting that if you test this without the 'target="_blank"' (i.e. the PDF opens in the same tab), the 'resource.received' event will be emitted (with null content type), but loading the resource will fail:
[warning] [phantom] Loading resource failed with status=fail: file:///opt/templates/templates/src/main/resources/casperjs/test.pdf
Is there any good way to handle links that will open/download PDFs in some generic way? You can hook into 'navigation.requested' perhaps and download there, but I don't think there's a wonderful way to figure out that the nav is for a PDF (the URL may not always have file extension).

Related

Elements not found after switching to iframe context in TestCafe

Original question:
using
browser.switchToFrame(iframeEl);
I can switch to a particular iframe window, and that's alright - clicking elements and etc works.
But, for whatever reason, using Selector when the iframe is the current context, does not work. I suspect that it's because switchToFrame is a method on the browser instance, and I'm using Selector function imported in such manner:
import { Selector } from 'testcafe';
My question is - if I want to select a particular element within the iframe using testcafe (to read its HTML attributes for example) - how should I approach it? Am I missing something?
More details from GitHub thread:
More details: I'm creating an iframe with remote src, and to that iframe, I later inject some HTML, CSS, and JavaScript. I'm 100% sure that the iframe will have the DOM element that'd match my requested selector - but still, I get an error: Cannot obtain information about the node because the specified selector does not match any node in the DOM tree.
My code looks roughly like this:
const iframeEl = await Selector('a-iframe_inner[name="something"]');
if (await iframeEl.count === 0) {
await this.fBrowser.switchToMainWindow();
} else {
await this.fBrowser.switchToIframe(iframeEl);
}
const something = await Selector('.something');
And on a line with await Selector the code breaks. In my other tests, where I'm also accessing the iframe and click some element using await browser.click(someOtherThing); it works flawlessly.
I can also read the console state of the iframe without hassle.
I suspect that the content of the iframe element might not be ready yet, but I'm wondering how can I wait until it's ready? I've tried setting a timeout option to the Selector call, but it didn't change anything. Can you share any tips on how to delay getting a selector after switching to iframe context?
Solution:
Turned out that it was indeed a bug on my part. Sorry. For future gens: Iframe switching and using selectors should work all fine, at least in TestCafe v0.20.1. Just make sure that your selectors match and you are really in iframe context, not just think that you are there
There is no need to do anything special to make Selectors work in iframes. It should work as expected. If they do not wish to create a bug report in the official repository using this form, I would appreciate it if you provide an example that demonstrates the issue.
As for your question, I was not able to reproduce this problem in a simple example.
Test page:
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title></title>
</head>
<body>
<h1>Click me</h1>
<iframe id="frame" src="http://example.com" style="width: 500px; height: 500px;"></iframe>
</body>
</html>
Test code:
import { Selector } from 'testcafe';
fixture `Selector in iframe`
.page `../pages/index.html`;
const selector = Selector('h1');
test('test', async t => {
await t.click(selector);
console.log(await selector.innerText);
await t.switchToIframe('#frame');
await t.click(selector);
console.log(await selector.innerText);
});
All clicks work as expected and I was able to get innerText of the Selector successfully.
In addition, I would recommend you check what element really exists on a page, that Selector refers to the existing element and that the element has width and height greater than zero.

Test a Google Sheet add-on

I have created an add-on in Script Editor with Code.gs and Index.html. I choose Publish ==> Test as add-on... and then selected another google sheet in the dialog box. Clicking on Test opens that google sheet, but I don't see any taskpane that should be made by index.html, =myFunction() does not work either in cells.
Does anyone know how to test this add-on?
Edit 1: Code.gs:
function myFunction() {
return 100
}
Index.html:
<!DOCTYPE html>
<html>
<head>
<base target="_top">
</head>
<body>
super add-on
</body>
</html>
You can definitely test the sidebar add-on, in other sheet. You need to use the below script. Also, make sure you select INSTALLATION CONFIG as Installed & Enabled.
function onOpen() {
var html = HtmlService.createHtmlOutputFromFile('index') //your html page name
.setTitle('My custom sidebar')
.setWidth(300);
SpreadsheetApp.getUi() // Or DocumentApp or FormApp.
.showSidebar(html);
}
Currently, custom functions are not working in test add-on mode. There is already an issue reported for this and Google as accepted it. Check this.

PhantomJS rewriting URL in backgroundImage property to local file system

I am using PhantomJS to do some rewriting of HTML. I'm adding a background-image property to an element. But when I write out the resulting DOM, the URL has been rewritten to a local URL. I've boiled this down to the following test case:
JS
var page = require('webpage').create();
page.open("test.html",function(){
setTimeout(function(){
page.evaluate(function(){
document.getElementById("test").style.backgroundImage="url(test.png)";
});
console.log(page.content);
phantom.exit();
},1000);
});
HTML
<html>
<body>
<div id="test"></div>
</body>
</html>
Output
$ phantomjs test.js
<html><head></head><body>
<div id="test" style="background-image: url(file:///C:/cygwin/tmp/test.png); ">
</div>
</body></html>
UPDATE
The problem remains if you specify ./test.png or //test.png. However, http://example.com/test.png is left unchanged, as might be expected.
If this HTML document is opened in Chrome, and the background-image property added to the div element in the style inspector, the URL is unmodified, whether the document is inspected in the Elements tab in devtools, or via document.body.innerHTML displayed in the console, or copying the HTML.
UPDATE 2
I just found out that if the document is located in Chrome, and the command elt.style.backgroundImage="url(test.png"); is issued in the console, then the URL is rewritten. So at the end of the day it appears that this is not a PhantomJS issue, although I still don't understand this behavior.
Obviously, I don't want this URL to be rewritten in this fashion, and I don't understand why PhantomJS feels the need to do this. Ideas?

constant spin loading but no image popping up - colorbox

When clicking the links, I get the popup box as expected however the images won't load, it just spins and spins. all the paths are ok as far as I can see.
HTML:
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.6.4/jquery.min.js"></script>
<link rel="stylesheet" href="colorbox/colorbox.css" />
<script src="colorbox/jquery.colorbox.js"></script>
<p><a class="group1" href="http://www.paycoservices.co.uk/colorbox/content/ohoopee1.jpg" title="Me and my grandfather on the Ohoopee.">Grouped Photo 1</a></p>
<p><a class="group1" href="http://www.paycoservices.co.uk/colorbox/content/ohoopee1.jpg" title="On the Ohoopee as a child">Grouped Photo 2</a></p>
<p><a class="group1" href="http://www.paycoservices.co.uk/colorbox/content/ohoopee1.jpg" title="On the Ohoopee as an adult">Grouped Photo 3</a></p>
JS
$(document).ready(function(){
//Examples of how to assign the Colorbox event to elements
$(".group1").colorbox({rel:'group1'});
$(".group2").colorbox({rel:'group2', transition:"fade"});
$(".group3").colorbox({rel:'group3', transition:"none", widt h:"75%", height:"75%"});
$(".group4").colorbox({rel:'group4', slideshow:true});
$(".ajax").colorbox();
$(".youtube").colorbox({iframe:true, innerWidth:640, innerHeight:390});
$(".vimeo").colorbox({iframe:true, innerWidth:500, innerHeight:409});
$(".iframe").colorbox({iframe:true, width:"80%", height:"80%"});
$(".inline").colorbox({inline:true, width:"50%"});
$(".callbacks").colorbox({
onOpen:function(){ alert('onOpen: colorbox is about to open'); },
onLoad:function(){ alert('onLoad: colorbox has started to load the targeted content'); },
onComplete:function(){ alert('onComplete: colorbox has displayed the loaded content'); },
onCleanup:function(){ alert('onCleanup: colorbox has begun the close process'); },
onClosed:function(){ alert('onClosed: colorbox has completely closed'); }
});
$('.non-retina').colorbox({rel:'group5', transition:'none'})
$('.retina').colorbox({rel:'group5', transition:'none', retinaImage:true, retinaUrl:true});
//Example of preserving a JavaScript event for inline calls.
$("#click").click(function(){
$('#click').css({"background-color":"#f00", "color":"#fff", "cursor":"inherit"}).text("Open this window again and this message will still be here.");
return false;
});
});
and a jsfiddle http://jsfiddle.net/Kuaet/2/
Chrome console gives these errors which are general as far as I can see and not related to this (although I know, they need sorting!)
GET http://www.paycoservices.co.uk/resources/demos/style.css 404 (Not Found) newsliderdev.asp:20
GET http://www.paycoservices.co.uk/ahkerrigan-light-webfont.woff 404 (Not Found) newsliderdev.asp:1
Resource interpreted as Font but transferred with MIME type application/octet-stream: "http://www.paycoservices.co.uk/ahkerrigan-light-webfont.ttf".
After using various versions of colorbox and jQuery I finally found a set that works well together and solves this issue as it was simply down to the versions of colorbox and jQuery I was using. jQuery 1.6.4 and the current version of colorbox work together perfectly.

dojo 1.8: loading dojo-laced html files into contentpane

Hi Any idea how I can load dojo-laced html file dynamically into contentpanes?
I am able to load non-dojo html into content pane using href.
When I loaded dojo-laced html file, I can see text in html tags but not text in dojo scripts. Where did I go wrong?
The scripts I put here are:-
widget.set('href','dojotext.html')
Another problem in jsfiddle is that pressing button 1 will not update, unlike in my environment.
and funny thing is that border container and comtent panes are not displayed, unlike in my environment too.
Here are my links in jsfiddle
- main page for testing loading
- dojo content to be loaded
Please advise. Thanks
Clement
First of all, your ContentPanes and BorderContainer are not being displayed because you're not parsing them.
In your code, you can run parser manually:
ready(function () {
parser.parse();
// ...
});
Regarding your first question, it seems that you didn't read the documentation:
<div id="foo" data-dojo-type="dijit/layout/ContentPane" href="/some/page.html">
<script type="dojo/method">
alert ('Hello World!');
</script>
</div>
Code from: ContentPane documentation