script tag breaks sightly data-sly tag in author mode - angularjs

I am using angular with sightly. So I have angular html template surrounded by script tag, which also has sightly attributes like data-sly-resource.
Below example code will give you clear idea.
<script type="text/ng-template" id="example.html">
<section data-sly-resource="${ #path='textOverImage', resourceType='example/components/textOverImage'}" id="textOverImage" >
<div ng-include="'private/textOverImage.html'" data-sly-test="${!wcmmode.edit}"></div>
</section>
</script>
It works fine in non-edit mode , but in edit mode, I can not author data-sly-resource part. It looks like <script> tag is not letting it work roperly because when I remove <script> tag ,than I can author it.
And removing script tag is not an option as well.
So how can I stop script tag form breaking sightly functionality in edit mode?

I ended up doing repetition of code , one for author mode and other for non edit mode.
Below is close resemblance of my solution.
<section data-sly-resource="${ #path='textOverImage', resourceType='example/components/textOverImage'}" id="textOverImage" data-sly-test="${wcmmode.edit}" >
<div ng-include="'private/textOverImage.html'"></div>
</section>
<script type="text/ng-template" id="example.html" data-sly-test="${!wcmmode.edit}">
<section data-sly-resource="${ #path='textOverImage', resourceType='example/components/textOverImage'}" id="textOverImage" >
<div ng-include="'private/textOverImage.html'"></div>
</section>
</script>
As you can see in above code, what to show and when works via data-sly-test="${wcmmode.edit}".
I also tried to to create sightly template for redundant code and than try data-sly-use but now, it works in author mode but sightly can't put template inside <script> tag even though I used # context='unsafe'

There is a workaround based on the Sightly Reference
Put the markup inside a separate html file say mymarkup.html parallel to mycomponent.html
In Component HTML file (e.g mycomponent.html) use <script type="text/ng-template" data-sly-include="mymarkup.html"></script>
In mymarkup.html we can use Sightly tags normally and those would be evaluated/executed normally, we would not even need to specify the # context for variables we would read using use API. The final markup rendered by component mycomponent.html when dragged to page would render something like this below
<script type="text/ng-template">
//mymarkup.html evaluated content here
</script>

In your script tag you could add data-sly-unwrap="${wcmmode.edit}"
This will remove script tag in edit mode allowing you to edit included components but in any other mode the script tag gets rendered.

I found the following mention in Netcentric's AEM Sightly Style Guide:
Then, because the HTML grammar ignores elements located inside a
< script > or < style > elements, no block statement can be used within
them.
Although it's not explicitly stated in the Sightly spec, it makes sense. So your fix is right.

Related

Angular UI bootstrap Modal is not working with AEM and sightly

In my application, I am using Angular UI bootstrap with AEM and having the sightly parameters in the same.
The issue is, when I try to access the sightly parameters inside the script tag of UI modal It is not rendenring the sightly parameters.
< script type="text/ng-template" id="/view2.tpl" data-sly-include="template.html">
${properties.title}
< /script >
This specific problem is there with Sightly with AEM and angular. Can anyone suggest how to make a Modal work for Angular+AEM+sightly?
Help will be highly appreciated.
As per the specification, using data-sly-include will cause the content of the <script> tag to be replaced with the content of the included script.
If you want to use HTL/Sightly templates from template.html you should instead write data-sly-use.tpl="template.html"
First, for using templates, use the data-sly-use instead of data-sly-include.
Second, HTL (Sightly) escapes the expressions by default depending on the context where they are used. You can explicitly specify the context using the context option as shown below.
<script type="text/ng-template" id="/view2.tpl">
<!--/* Use scriptString if you are using the value as a string */-->
${properties.title # context='scriptString'}
<!--/* In case you are trying to output an entire function or javascript,
there is no context specifically available for that. So, you can use the
unsafe option to disable escaping completely */-->
${properties.title # context='unsafe'}
</script>
More information on Display Context can be found here and information on Template and Call here.

Angular Ui Boostrap Popover with html inline how to scape or encode the innerhtml

I´m migrating from a really old version of ui-boostrap to the new one.
On the previous version we have only popover="myhtml"
Now is needed to have popover-html and sanatize the html.
The problem is when we have the html inline, when we have the html on a variable of the scope is simple as
uib-popover-html="getPopoverContent(searchResultHtml)"
But the ones that were with the html inline, when i try to use the same syntaxis fails becouse uib-popover-html="getPopoverContent('theHtml')"
theHtml normally have quotes who breaks all
Example of the function that fails
uib-popover-html="getPopoverContent('<ul class="list-unstyled"><li><span class="text-muted">true_ip:</span> {{txn.thm_info.true_ip}}</li>"')
The problem is that the double quotes closes the uib-popover-html, so get broken all.
What is needed here, I tried to scape with / the inner quotes,but failed.
I know that the correct way is do templates, is only for do a quick migration to allow us to gain more time to later migrate all things.
Thanks
You know that the right thing to do is to use a template, and you have an angular expression anyway inside your HTML, so a template is required.
So just do the right thing, and use a template. Don't try to find nasty shortcuts. That will make the code much cleaner as a bonus.
<script type="text/ng-template" id="myPopoverTemplate.html">
<ul class="list-unstyled">
<li><span class="text-muted">true_ip:</span> {{ txn.thm_info.true_ip }}</li>
</ul>
</script>
<button uib-popover-template="'myPopoverTemplate.html'" ...>

AngularJS: Script tag not working in ng-include

I have a file index.html with the following code:
<div ng-include="'fragment-1.html'"></div>
The code of fragment-1.html:
<b>Inside Fragment 1</b>
<script type="text/javascript">
alert("Inside Fragment 1");
</script>
When I load index.html into the browser, output is:
Inside Fragment 1
The DOM has the <script> tags but the alert is not shown.
My hypothesis:
Because the DOM loads first along with the Angular modules and then Angular checks and binds the data(in this case, fragment-1.html file content) to the view(index.html), it just adds the elements of fragment-1.html in DOM. To execute the JS inside fragment-1.html, we should create a hack for it. Am I right in this explanation? Or is there something else that I may be missing?
I had to load jQuery before loading Angular. The explanation is in the link specified above. Explanation: script not running in templateurl
To include another partial HTML file in your parent HTML file, one can also use Angular directives, depending on the situation. See this answer for when to use ng-include and when to use directives: https://stackoverflow.com/a/24172025/3132646
You don't need to hack. Angular gives you a neat and simple solution to what you want to achieve with your code.
Controller
.controller('fragmentOneCtrl', function ($scope) {
alert('"Inside Fragment 1"');
})
View
<div ng-repeat="go in ['go', 'gogo']" ng-include="'includeThis'">
</div>
<script type="text/ng-template" id="includeThis">
<div ng-controller="fragmentOneCtrl">
</div>
</script>
You may want to use $sce.trustAsHtml before injecting the resource in html

How To Source Bootstrap Popover Template From File?

I am using angularjs ui bootstrap, and I have my popover template all set up and working. Here is what I have.
directive.html
...
popover-title="Title"
popover-template="'popover.template.html'"
...
A bit lower in the same directive I have the template:
<script type="text/ng-template" id="popover.template.html">
<label>Popup Title:</label>
<span>Popup content</span>
</script>
Now I will need this popover for a few elements, so how can I put it in an actual popover.template.html file in my source tree I just made in the same directory in the simplest way (least lines of code) possible?
The solution was this:
leave the script tags needed for inline tags behind
give the template parameter the full path
create a new file in the desired place, no header needed inside
then add to the element you want popover to work on this:
popover-template="'app/templates/popover.template.html'"
No need for templateCache or any other tricks, the site only sends a single request, even with multiple elements using the same template. It loads on first request.

How can I insert text from an external file onto a div?

As the title says; I want the content of an external file (text,html,php etc.) onto a div.
There is basically text in an external file, called: text_1.txt or *text_1.html* , and I want that text displayed within a div that is located on a homepage.
The perfect solution would be a pretty basic code to display text from a text or html file
by inserting it onto a div classed: content
Here I have illustrated the issue with basic code, use this as an example to write a solution.
Code in text_1.html:
<p>Hello world.</p>
Code in index.html:
<!doctype html>
<html>
<head>
<title>Homepage</title>
</head>
<body>
<div class="content"></div>
</body>
</html>
This is as simple as I can put it.
I highly appreciate all the answers I receive, thank you.
PS here are some things you should avoid answering:
Use iframes, or any other frame type solution.
Make use of the onclick function within jquery etc.
Use ineffective textfields to replace certain text.
Make usage of an insertion code for virtual server or similar methods.
There's no way to do this unless and until you use Server Side Includes using PHP, ASP, or JSP
http://en.wikipedia.org/wiki/Server_Side_Includes
If you want to do it using php you can use this:
require_once('filename.php'); /* For including files */
Or use native functions to open .txt files in your pages
Why dont you just do it with jquery
$(document).ready(function() {
$('.content').load('text_1.html');
});

Resources