QT Installer Controller Script crash while "addWizardPage" - qt

I got some problems with the QT Installer - already done all tutorials (especially http://doc.qt.io/qtinstallerframework/noninteractive.html) but i am still a real newbie
What i need:
an installer with a language Selection as first page
adding a second (save) path in TargetDirectory
What i have:
an installscript.js (package root)
an ControlScript.js (path in config.xml)
What i tried in the ControlScript.js:
function Controller()
{
QMessageBox.information("DEBUG", "DEBUG", "DEBUG", QMessageBox.Ok);
installer.addWizardPage(component, "Start", QInstaller.Introduction);
QMessageBox.information("TEST", "TEST", "TEST", QMessageBox.Ok);
}
the Start.ui i placed at the config path and package root but nothing happens... the second MessageBox is never shown - the installer seems to be crashed
function Controller()
{
}
Controller.prototype.IntroductionPageCallback = function()
{
installer.addWizardPageItem(component ,"lineEdit",QInstaller.TargetDirectory);
}
same - nothing happens here installer crashed
hope you can help me to fix the code =)
and can someone please tell me how to change the language or setting a new pixmap (form an existing ressource) while the installer is running?
i wrote this incomplete code in installscript.js:
NewLanguageSeted = function()
{
var widget = gui.pageWidgetByObjectName("DynamicLanguageSelection");
QMessageBox.information("DEBUG", "DEBUG", "DEBUG", QMessageBox.Ok);
widget.Icon.setPixmap("");
installer.languageChanged();
QMessageBox.information("LanguageSelec", "LanguageSelec", "LanguageSelec", QMessageBox.Ok);
}
installer.languageChanged();
will Change all texts based on *.qm files - but how can i get / set the actual language?
widget.Icon.setPixmap("");
changes the pixmap - but i need to know what i have to insert in ""
for the ui file i use a resource file:
<property name="pixmap">
<pixmap resource="../../../resource/resource.qrc">:/DuerrPictures/watermark.png</pixmap>

As far as I know, installer pages canno't be added from the controller script. If you run the installer from QtCreator, you will see the corresponding debug output, which says something like component type is not defined.
To add the page you have to do it inside of the component script (e.g. the constructor). This one will be executed immediatly after you selected one of the 3 checkboxes. The .ui-file has to be part of the package, too:
Regarding the second linedit - It is the same problem! The function takes a component as argument - it has to be done inside the installscript.js.
installscript.js:
function Component()
{
QMessageBox.information("DEBUG", "DEBUG", "DEBUG", QMessageBox.Ok);
installer.addWizardPage(component, "Start", QInstaller.Introduction);
installer.addWizardPageItem(component ,"lineEdit",QInstaller.TargetDirectory);
QMessageBox.information("TEST", "TEST", "TEST", QMessageBox.Ok);
}
The pixmap should be settable by using the very same path you used in your .ui-file, i.e. :/DuerrPictures/watermark.png. Have your tried that?
And for your language problem - sorry, but I don't know anything about that. Check out the Scripting API - all script classes are listed there, maybe you can find something.

Related

Initialising a driver instance with callSingle does not work for automated UI tests [duplicate]

I was trying to find a way to launch all features in Karate testing through maven using an external variable to set up the browser (with a local webdriver or using a Selenium grid).
So something like:
mvn test -Dbrowser=chrome (or firefox, safari, etc)
or using a Selenium grid:
mvn test -Dbrowser=chrome (or firefox, safari, etc) -Dgrid="grid url"
With Cucumber and Java this was quite simple using a singleton for setting up a global webdriver that was then used in all tests. In this way I could run the tests with different local or remote webdrivers.
In Karate I tried different solution, the last was to:
define the Karate config file a variable "browser"
use the variable "browser" in a single feature "X" in which I set up only the Karate driver
from all the other features with callonce to re-call the feature "X" for using that driver
but it didn't work and to be honest it doesn't seem to me to be the right approach.
Probably being able to set the Karate driver from a Javascript function inside the features is the right way but I was not able to find a solution of that.
Another problem I found with karate is differentiating the behavior using a local or a remote webdriver as in the features files they're set in different ways.
So does anyone had my same needs and how can I solve it?
With the suggestions of Peter Thomas I used this karate-config.js
function fn() {
// browser settings, if not set it takes chrome
var browser = karate.properties['browser'] || 'chrome';
karate.log('the browser set is: ' + browser + ', default: "chrome"');
// grid flag, if not set it takes false. The grid url is in this format http://localhost:4444/wd/hub
var grid_url = karate.properties['grid_url'] || false;
karate.log('the grid url set is: ' + grid_url + ', default: false');
// configurations.
var config = {
host: 'http://httpstat.us/'
};
if (browser == 'chrome') {
if (!grid_url) {
karate.configure('driver', { type: 'chromedriver', executable: 'chromedriver' });
karate.log("Selected Chrome");
} else {
karate.configure('driver', { type: 'chromedriver', start: false, webDriverUrl: grid_url });
karate.log("Selected Chrome in grid");
}
} else if (browser == 'firefox') {
if (!grid_url) {
karate.configure('driver', { type: 'geckodriver', executable: 'geckodriver' });
karate.log("Selected Firefox");
} else {
karate.configure('driver', { type: 'geckodriver', start: false, webDriverUrl: grid_url });
karate.log("Selected Firefox in grid");
}
}
return config;
}
In this way I was able to call the the test suite specifying the browser to use directly from the command line (to be used in a Jenkins pipeline):
mvn clean test -Dbrowser=firefox -Dgrid_url=http://localhost:4444/wd/hub
Here are a couple of principles. Karate is responsible for starting the driver (the equivalent of the Selenium WebDriver). All you need to do is set up the configure driver as described here: https://github.com/intuit/karate/tree/master/karate-core#configure-driver
Finally, depending on your environment, just switch the driver config. This can easily be done in karate-config.js actually (globally) instead of in each feature file:
function fn() {
var config = {
baseUrl: 'https://qa.mycompany.com'
};
if (karate.env == 'chrome') {
karate.configure('driver', { type: 'chromedriver', start: false, webDriverUrl: 'http://somehost:9515/wd/hub' });
}
return config;
}
And on the command-line:
mvn test -Dkarate.env=chrome
I suggest you get familiar with Karate's configuration: https://github.com/intuit/karate#configuration - it actually ends up being simpler than typical Java / Maven projects.
Another way is to set variables in the karate-config.js and then use them in feature files.
* configure driver = { type: '#(myVariableFromConfig)' }
Keep these principles in mind:
Any driver instances created by a "top level" feature will be available to "called" features
You can even call a "common" feature, create the driver there, and it will be set in the "calling" feature
Any driver created will be closed when the "top level" feature ends
You don't need any other patterns.
EDIT: there's some more details in the documentation: https://github.com/intuit/karate/tree/develop/karate-core#code-reuse
And for parallel execution or trying to re-use a single browser for all tests, refer: https://stackoverflow.com/a/60387907/143475

UIDocumentPickerViewController iOS13 not Working

On my application, i use UIDocumentPickerViewController to allow the user to pick files (import), but starting from iOS 13 that functionality stop working, basically the document picker is open, but the user can't choose a file (taping the file does nothing).
I made a simple sample just to isolate the code:
class ViewController: UIViewController, UIDocumentPickerDelegate {
#IBAction func openDocumentPicker(_ sender: Any) {
let types = [String(kUTTypePDF)]
let documentPickerViewController = UIDocumentPickerViewController(documentTypes: types, in: .import)
documentPickerViewController.delegate = self
present(documentPickerViewController, animated: true, completion: nil)
}
func documentPickerWasCancelled(_ controller: UIDocumentPickerViewController) {
print("Cancelled")
}
func documentPicker(_ controller: UIDocumentPickerViewController, didPickDocumentsAt urls: [URL]) {
print("didPickDocuments at \(urls)")
}
}
Sample project:
https://github.com/Abreu0101/document-picker-iOS13-issue
Reference:
When I got this issue, I realised that it's working when choosing files from "Browse" tab because I implemented the method "didPickDocumentAt", but it was not working when I tapped on files from "Recent" tab.
To make it work on "Recent" tab, I'd to implement the method "didPickDocumentsAt", which makes the same thing, but it handles an array of URLs.
On Mojave there's the problem, make sure you upgrade your os to Catalina.
https://github.com/Elyx0/react-native-document-picker/issues/246
UIDocumentBrowserViewController error "Cannot create urlWrapper for url" on iOS13 simulator
I enountered this issue on iOS 13.2.2. Updated to iOS 13.2.3 fixed this issue without any code changes.

How to get outputs of one Rule item as inputs of another one?

I want to create automatic crossplatform installation builder for my project. For this reason I made this file myprojectpackage.qbs:
Product {
type: "mypackage"
Depends { name: "myproject" } // <- this one has type "application"
Depends { name: "applicationpackage" }
}
applicationpackage.qbs uses some submodules and looks like:
Module {
name: "applicationpackage"
Depends { name: "qtlibsbinariespackage" }
Depends { name: "3rdpartybinariespackage" }
Depends { name: "resourcepackage" }
}
All these modules try to find something and copy to package directory. After they finish, I have a folder with a portable version of application. Every module of this group have typical structure:
Module {
name: "somepackage"
Rule {
condition: qbs.targetOS.contains("windows")
multiplex: true
alwaysRun: true
inputsFromDependencies: ["application"]
Artifact {
filePath: "Copied_files.txt"
fileTags: "mypackage"
}
prepare: {
var cmdQt = new JavaScriptCommand()
// prepare paths
cmdQt.sourceCode = function() {
// copy some files and write to Copied_files.txt
}
return [cmdQt]
}
}
}
After portable folder package complete, I want to make a zip archieve. So, I need another Module, which will run after package modules. I think, that only way to do like this is taking .txt files, that were created by modules in applicationpackage, as inputs for another Rule.
I have tried a lot of things (FileTaggers, outputFileTags etc.), but noone worked properly. So is there any way to do make modules work in pipeline as I want to do?
Do I understand correctly that you want to "merge" the contents of the txt files tagged "mypackage" into the archive, i.e. everything listed in all the files is supposed to end up there?
If so, then you simply need a "top-level" rule that does the aggregation. Your existing rules would tag their outputs as e.g. "mypackage.part" and then a multiplex rule would take these as inputs and create a "mypackage" artifact.
Note that there is the archiver module (https://doc.qt.io/qbs/archiver-module.html) that can do the final step of creating the package for you from the aggregated txt file.

Meteor Package: Add Custom Options

I've created a Meteor smart package, and would like to add user generated custom options to the API.
However, I'm having issues due to Meteor's automatic load ordering.
SocialButtons.config({
facebook: false
});
This runs a config block that adds defaults.
SocialButtons.config = function (options) {
... add to options if valid ...
};
Which in turn grabs a set of defaults:
var defaults = {
facebook: true,
twitter: true
}
Which are mixed into the settings.
var settings = _.extend(defaults, options);
...(program starts, uses settings)...
The problem is that everything must run in the proper order.
Create SocialButtons object
Run the optional SocialButtons.config()
Create settings & run the program
How can I control the load order in Meteor without knowing where a user might place the optional configuration?
Step 2 will be in a different folder/file, but must run sandwiched between steps 1 & 3.
You can't really control load order right now so it's not guaranteed but placing files at /libs are loaded first but in your case it's doesn't really matter it might be something else here is a very simple package you can view the source on how I setup default options and allow to replace those easily https://github.com/voidale/meteor-bootstrap-alerts
Figured this out.
Put your package into a /lib directory.
Include a setup function that sets the settings when called, and loads the data
Return the data from the startup function
In this case:
SocialButtons.get = function () {
return initButtons();
}
function initButtons() { ... settings, startup, return final value ... }

Marionette js itemview not defined: then on browser refresh it is defined and all works well - race condition?

Yeah it's just the initial browser load or two after a cache clear. Subsequent refreshes clear the problem up.
I'm thinking the item views just aren't fully constructed in time to be used in the collection views on the first load. But then they are on a refresh? Don't know.
There must be something about the code sequence or loading or the load time itself. Not sure. I'm loading via require.js.
Have two collections - users and messages. Each renders in its own collection view. Each works, just not the first time or two the browser loads.
The first time you load after clearing browser cache the console reports, for instance:
"Uncaught ReferenceError: MessageItemView is not defined"
A simple browser refresh clears it up. Same goes for the user collection. It's collection view says it doesn't know anything about its item view. But a simple browser refresh and all is well.
My views (item and collection) are in separate files. Is that the problem? For instance, here is my message collection view in its own file:
messagelistview.js
var MessageListView = Marionette.CollectionView.extend({
itemView: MessageItemView,
el: $("#messages")
});
And the message item view is in a separate file:
messageview.js
var MessageItemView = Marionette.ItemView.extend({
tagName: "div",
template: Handlebars.compile(
'<div>{{fromUserName}}:</div>' +
'<div>{{message}}</div>' +
)
});
Then in my main module file, which references each of those files, the collection view is constructed and displayed:
main.js
//Define a model
MessageModel = Backbone.Model.extend();
//Make an instance of MessageItemView - code in separate file, messagelistview.js
MessageView = new MessageItemView();
//Define a message collection
var MessageCollection = Backbone.Collection.extend({
model: MessageModel
});
//Make an instance of MessageCollection
var collMessages = new MessageCollection();
//Make an instance of a MessageListView - code in separate file, messagelistview.js
var messageListView = new MessageListView({
collection: collMessages
});
App.messageListRegion.show(messageListView);
Do I just have things sequenced wrong? I'm thinking it's some kind of race condition only because over 3G to an iPad the item views are always undefined. They never seem to get constructed in time. PC on a hard wired connection does see success after a browser refresh or two. It's either the load times or the difference in browsers maybe? Chrome IE and Firefox on a PC all seem to exhibit the success on refresh behavior. Safari on iPad fails always.
PER COMMENT BELOW, HERE IS MY REQIRE BLOCK:
in file application.js
require.config({
paths: {
jquery: '../../jquery-1.10.1.min',
'jqueryui': '../../jquery-ui-1.10.3.min',
'jqueryuilayout': '../../jquery.layout.min-1.30.79',
underscore: '../../underscore',
backbone: '../../backbone',
marionette: '../../backbone.marionette',
handlebars: '../../handlebars',
"signalr": "../../jquery.signalR-1.1.3",
"signalr.hubs": "/xyvidpro/signalr/hubs?",
"debug": '../../debug',
"themeswitchertool": '../../themeswitchertool'
},
shim: {
'jqueryui': {
deps: ['jquery']
},
'jqueryuilayout': {
deps: ['jquery', 'jqueryui']
},
underscore: {
exports: '_'
},
backbone: {
deps: ["underscore", "jquery"],
exports: "Backbone"
},
marionette: {
deps: ["backbone"],
exports: "Marionette"
},
"signalr": {
deps: ["jquery"],
exports: "SignalR"
},
"signalr.hubs": {
deps: ["signalr"],
exports: "SignalRHubs"
},
"debug": {
deps: ["jquery"]
},
"themeswitchertool": {
deps: ["jquery"]
}
}
});
require(["marionette", "jqueryui", "jqueryuilayout", "handlebars", "signalr.hubs", "debug", "themeswitchertool"], function (Marionette) {
window.App = new Marionette.Application();
//...more code
})
Finally, inside the module that uses creates the collection views in question, the list of external file dependencies is as follows:
var dependencies = [
"modules/chat/views/userview",
"modules/chat/views/userlistview",
"modules/chat/views/messageview",
"modules/chat/views/messagelistview"
];
Clearly the itemViews are listed before collectionViews. This seems correct to me. Not sure what accounts for the collectionViews needing itemViews before they are defined. And why is all ok after a browser refresh?
The sequence in which you load files is most likely wrong: you need to load the item view before the collection view.
Try putting all of your code in the same file in the proper order, and see if it works.
The free preview to my book on Marionette can also guide you to displaying a collection view.
Edit based on calirification:
The dependencies listed for the module are NOT loaded linearly. That is precisely what RequireJS was designed to avoid. Instead the way to get the files loaded properly (i.e. in the correct order), is by defining a "chain" of dependencies that RequireJS will compute and load.
What you need to do is define (e.g.) your userlistview to depend on userview. In this way, they will get loaded in the proper order by RequireJS. You can see an example of a RequireJS app here (from by book on RequireJS and Marionette). Take a look at how each module definition decalre which modules it depends on (and that RequireJS therefore needs to load before). Once again, listing the modules sequentially within a dependecy array does NOT make them get loaded in that sequence, you really need to use the dependency chain mechanism.

Resources