/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */
 
<%-- used by ScriptBuiltinObjectsTest --%>
<html>
	<body>
		<h1>ESP template</h1>
		<p>currentNode.text:<%= currentNode.text %></p>
	</body>
	
	<!-- 
		TODO we should test access to a well-known service
		via the ServiceLocator - for now just check that it's
		available 
	-->
	<%
		var sc = sling.getService(Packages.java.lang.String);
	%>
	<p>sc:<%= sc %></p>
	
	<!-- test access to Response -->
	<p>SlingHttpServletResponse:<%= response.containsHeader('NOT_A_HEADER') %></p>
	
	<!-- sling object is tested elsewhere (IncludeTest) -->
	
</html>
