Skip to main content
Announcements
Have questions about Qlik Connect? Join us live on April 10th, at 11 AM ET: SIGN UP NOW
cancel
Showing results for 
Search instead for 
Did you mean: 
Not applicable

Angular 2 and qlik iframe

Hi Experts,

We have an angular 2 application (generated with angular-cli) with an iframe integration. I have generated an child component (so next to the standard "app" component, I have "child" component. Via the Qlik Explorer for Developers we can have some simple generated code to get some server connection boiler plate code (see below). I want to know what the user selected in the iframe, that's why I would like to have the qlik config with require components. I know it works when I just load the qlik app directly and put the js code from the qlik.js file in a script tag in the index.html. But when I want to load it dynamically (e.g. import it in a component), I get an error. Is this even possible?

I hope it is clear what I'm trying to achieve.

In the index.html I have the following script tag

    <script src="https://playground.qlik.com/resources/assets/external/requirejs/require.js"></script>

In my components folder I have the following file: qlik.js with the following code:

var config = {

    host: 'playground.qlik.com',

    prefix: '/',

    port: 443,

    isSecure: true

};

require.config({

    baseUrl: ( config.isSecure ? "https://" : "http://" ) + config.host + (config.port ? ":" + config.port : "") + config.prefix + "resources"

});

require(["js/qlik"], function (qlik) {

    "use strict";

    var app;

    qlik.setOnError(function (error) {

        // empty for now

    });

    function attach(elem) {

        var appid;

        appid = elem.dataset.qlikAppid;

        app = qlik.openApp(appid, config);

    }

    function dispatchQlikValue(array) {

        var selState, listener;

        if (array === undefined) {

            throw new Error("Qlik element array not found");

        }

        attach(array[0]);

        console.log("Current app: ", app);

        selState = app.selectionState();

        listener = function () {

            var dataType, event;

            if (selState.selections.length > 0) {

                dataType = selState.selections.filter(function (value) {

                    return value.fieldName === "DataType";

                });

                if (dataType.length === 0) {

                    event = new CustomEvent("selectionEvent", {

                        detail: selState.selections,

                        bubbles: true,

                        cancelable: true

                    });

                    document.dispatchEvent(event);

                }

            }

        };

        selState.OnData.bind(listener);

    }

    var element = document.getElementsByClassName("qlik-embed");

    if (element.length > 0) {

        dispatchQlikValue(element);

    }

});

I'm importing this in my cmponent like this:

import {Component} from "@angular/core";

import "./qlik.js";

But I'm getting the following error:

zone.js:388 Unhandled Promise rejection: Cannot find module "js/qlik" ; Zone: <root> ; Task: Promise.then ; Value: Error: Cannot find module "js/qlik"(…) Error: Cannot find module "js/qlik"

    at webpackMissingModule (http://localhost:4200/main.bundle.js:105837:172)

    at http://localhost:4200/main.bundle.js:105837:256

    at ZoneDelegate.invoke (http://localhost:4200/main.bundle.js:104578:26)

    at Zone.run (http://localhost:4200/main.bundle.js:104460:43)

    at http://localhost:4200/main.bundle.js:104848:57

    at ZoneDelegate.invokeTask (http://localhost:4200/main.bundle.js:104611:35)

    at Zone.runTask (http://localhost:4200/main.bundle.js:104500:47)

    at drainMicroTaskQueue (http://localhost:4200/main.bundle.js:104747:35)

3 Replies
websy1985
Luminary Alumni
Luminary Alumni

Hi Jermaine,

I think the actual problem here is authentication. You're requesting the require.js resource from the default virtual proxy (prefix: '/') which doesn't allow anonymous access. That means your request for the require.js file is silently redirecting to a login screen and subsequently failing which is why you're getting that error. You should be able to validate this by inspecting the network tab in the browser developer tools.

Depending on what app you're trying to use you may be able to use the /showcase virtual proxy which allows anonymous access but only exposes apps that are part of the showcase solutions. Otherwise you can authenticate by using the same authentication flow provided in the "Basic Capability API Template" and use the /playground virtual proxy. Another example can be found in the "Untappd Capability API Dashboard".

That's not to say that your solution will work immediately once you're authenticated but it's a start. By loading the Capability APIs into your page you're also loading AngularJS 1.5 which means you'll be running 2 versions of angular in the same page. Not sure if you'll have issues there or not, it's not something I've done before.

I hope that helps.

Thanks

Nick

Not applicable
Author

Hi Nick,

Thanks for the answer, but it works fine when I just load everything via script tags in the index.html (head section) and I load my component with an Qlik app. If I load the script in the head section, I need to load at least my component or it will not find the css class it's looking for. In my case "qlik-embed".

But I want it to load dynamically (not in the head section) because I need to do some calculations on beforehand.

Not applicable
Author

I will try to make some example code asap.