Forum Discussion
Invalid Package - Sharepoint Framework Extensions
- Jun 07, 2017
Issue was in the elements.xml file, but not in encoding. More obvious than that, but still hard to catch. App catalow actually has actually "unavailable apps" link, which provides details on the possible errors and it's typically really accurate.
If you open up the elements.xml file from the sharepoint/assets folder, you can see that the last Elements element is missing closing tag, like defined in above exception. Below is the original Elements.xml file content and you can see that we are missing final > closing. After adding that missing character there, it was all good for deployment.
<?xml version="1.0" encoding="utf-8"?> <Elements xmlns="http://schemas.microsoft.com/sharepoint/"> <CustomAction Title="SPFxApplicationCustomizer" Location="ClientSideExtension.ApplicationCustomizer" ClientSideComponentId="43833b44-df29-40bf-aec2-294dd435ee05"> </CustomAction> </Elements
So - completely logical reason, was just hard to spot.
quick question.
What are the available placeholders? by debugging I could see that is PageHeader, PageFooter, and DialogContainer in other pages.
What I am trying to achieve is to INJECT App Insights tracking code into the page.
I dont have any error, but according to App Insights documentation, I should put the code before the </head> element.
I tried different ways, but I just can get any kind of stats on Applicaiton Insights, my best guess its becase the code is not before the end head tag, and therefore if the placeholder does not exist, then it will never work.
@override public onRender(): void { let html: string = ''; html+= `<script type="text/javascript"> "var appInsights=window.appInsights||function(config){ function i(config){t[config]=function(){var i=arguments;t.queue.push(function(){t[config].apply(t,i)})}}var t={config:config},u=document,e=window,o="script",s="AuthenticatedUserContext",h="start",c="stop",l="Track",a=l+"Event",v=l+"Page",y=u.createElement(o),r,f;y.src=config.url||"https://az416426.vo.msecnd.net/scripts/a/ai.0.js";u.getElementsByTagName(o)[0].parentNode.appendChild(y);try{t.cookie=u.cookie}catch(p){}for(t.queue=[],t.version="1.0",r=["Event","Exception","Metric","PageView","Trace","Dependency"];r.length;)i("track"+r.pop());return i("set"+s),i("clear"+s),i(h+a),i(c+a),i(h+v),i(c+v),i("flush"),config.disableExceptionTracking||(r="onerror",i("_"+r),f=e[r],e[r]=function(config,i,u,e,o){var s=f&&f(config,i,u,e,o);return s!==!0&&t["_"+r](config,i,u,e,o),s}),t }({ instrumentationKey:"b4cf6d1c-5d38-48ce-ac4e-8a7802f2a1a0", enableDebug: true, }) window.appInsights=appInsights; appInsights.trackPageView(); </script>`; console.log('CustomHeader.onRender()'); console.log('Available placeholders: ', this.context.placeholders.placeholderNames.join(', ')); // Handling header place holder if (!this._headerPlaceholder) { this._headerPlaceholder = this.context.placeholders.tryAttach( 'PageHeader', { onDispose: this._onDispose }); // The extension should not assume that the expected placeholder is available. if (!this._headerPlaceholder) { console.error('The expected placeholder was not found.'); return; } if (this.properties) { let headerString: string = this.properties.Header; if (!headerString) { headerString = '(Header property was not defined.)'; } if (this._headerPlaceholder.domElement) { this._headerPlaceholder.domElement.innerHTML = ` <div class="${styles.app}"> <div class="ms-bgColor-themeDark ms-fontColor-white ${styles.header}"> <i class="ms-Icon ms-Icon--Info" aria-hidden="true"></i> ${escape(headerString)}<p>hello world</p> <script type="text/javascript"> "var appInsights=window.appInsights||function(config){ function i(config){t[config]=function(){var i=arguments;t.queue.push(function(){t[config].apply(t,i)})}}var t={config:config},u=document,e=window,o="script",s="AuthenticatedUserContext",h="start",c="stop",l="Track",a=l+"Event",v=l+"Page",y=u.createElement(o),r,f;y.src=config.url||"https://az416426.vo.msecnd.net/scripts/a/ai.0.js";u.getElementsByTagName(o)[0].parentNode.appendChild(y);try{t.cookie=u.cookie}catch(p){}for(t.queue=[],t.version="1.0",r=["Event","Exception","Metric","PageView","Trace","Dependency"];r.length;)i("track"+r.pop());return i("set"+s),i("clear"+s),i(h+a),i(c+a),i(h+v),i(c+v),i("flush"),config.disableExceptionTracking||(r="onerror",i("_"+r),f=e[r],e[r]=function(config,i,u,e,o){var s=f&&f(config,i,u,e,o);return s!==!0&&t["_"+r](config,i,u,e,o),s}),t }({ instrumentationKey:"b4cf6d1c-5d38-48ce-ac4e-8a7802f2a1a0", enableDebug: true, }) window.appInsights=appInsights; appInsights.trackPageView(); </script> </div> </div>`; //this._headerPlaceholder.domElement.innerHTML = html; console.log('injected'); //alert('hello world'); } } } }
We have header and footer placeholders to start with. I, unfortunately, haven't had time to test app insights scenario yet, so not sure how it should be setup. Would though suggest that we get this discussion moved under a different topic in this developer space so that the title is accurate enough for other people looking to solve similar things.