[JavaScript] HTML 안의 자바스크립트

개요

자바스크립트는 등장과 동시에 HTML에 포함되었다. 자바스크립트는 HTML 페이지 렌더링을 방해하지 않으며 공존해야만 했다. 넷스케이프의 주도 아래 오늘날까지 살아남은 규칙을 소개한다. 아래의 규칙은 HTML 명세에 공식적으로 문서화된 내용이다. <script> 요소는 인라인 스크립트와 외부 스크립트 두 가지로 사용할 수 있다.


1. 인라인 스크립트

1
2
3
4
5
<script type="text/javascript">
function hello() {
alert("hello!");
}
</script>

위의 코드와 같이 <script> 요소 안에 직접 작성한 것을 말한다. 단, 여기에서 주의할 점이 있다. 인라인 스크립트를 사용할 경우 문자열 </script>는 사용할 수 없다.

1
2
3
4
5
<script type="text/javascript">
function hello() {
alert("</script>");
}
</script>

alert 안의 ""를 문자열이 아닌 닫는 태그로 인식하기 때문에 벌어지는 일이다. 이럴 때에는 ‘/’ 문자를 ‘\’(역슬래시)와 함께 사용하여 해결할 수 있다.

1
2
3
4
5
<script type="text/javascript">
function hello() {
alert("<\/script>");
}
</script>

2. 외부 스크립트

자바스크립트를 외부 파일에서 불러오려면 src 속성을 사용해야 한다.

1
2
3
4
// 1. 태그로 닫기
<script type="text/javascript" src="example.js"></script>
// 2. 인라인으로 닫기(IE에서는 제대로 처리되지 않을 때가 있다고 한다.)
<script type="text/javascript" src="example.js"/>

위의 코드는 외부 파일은 example.js를 페이지로 불러온다. 이 파일 안에는 절대 <script>, </script> 태그가 들어가서는 안 되며, 자바스크립트 코드만 들어 있어야 한다.

무엇보다 js 파일을 내려받아 실행한다면, 모든 인라인 코드는 무시된다는 점은 잊어선 안 된다.


어디에 위치시켜야 하는가?

전통적으로 js 파일은 <head> 요소 내에 위치시켰다. 그러나 자바스크립트 파일 해석이 끝날 때까지 페이지 렌더링이 지연되기 때문에 일반적으로 <body> 요소 안에, 콘텐츠 마지막에 쓴다.

1
2
3
4
5
6
7
8
9
10
11
12
<!DOCTYPE html>
<html>
<head>
<title>페이지 제목입니다.</title>
</head>
<body>
<p>페이지 콘텐츠 내용을 적고</p>
<!--페이지 콘텐츠-->
<script type="text/javascript" src="example1.js"></script>
<script type="text/javascript" src="example1.js"></script>
</body>
</html>

혹은 defer[1] 속성을 사용하는 방법이 있다. 이 속성은 스크립트에서 페이지 구조를 바꾸지 않는다고 명시하는 것이다. 페이지 전체를 파싱한 후 스크립트를 실행해도 상관없기 때문에, 브라우저는 defer 요소를 만나는 즉시 코드를 내려받지만 실행은 지연한다.

1
2
3
4
5
6
7
8
9
10
11
<!DOCTYPE html>
<html>
<head>
<title>페이지 제목입니다.</title>
<script type="text/javascript" defer src="example1.js"></script>
<script type="text/javascript" defer src="example1.js"></script>
</head>
<body>
<!--페이지 콘텐츠-->
</body>
</html>

그러나 인터넷 익스플로러 4, 파이어폭스 3.5, 사파리 5, 크롬 7 이상에서만 동작하기 때문에 여전히 스크립트는 페이지 맨 마지막에 놓는 것이 최상이다.


비동기 스크립트

async[2] 속성은 defer와 비슷하게 스크립트를 처리한다. 외부 스크립트에만 적용되며, 브라우저에게 파일을 즉시 내려받으라고 지시한다. 다만, defer와 다르게, 스크립트가 마크업 순서대로 실행된다는 보장이 없다.

즉, javascript 파일 사이에 의존성이 있으면 안 된다. example1.js가 자바스크립트 라이브러리 파일이고, example2.js파일이 해당 라이브러리를 이용한다면 example2.js 파일이 제대로 실행되지 않을 수도 있다. async 속성은 순서에 상관없이 실행해도 좋다는 의미를 내포한다.


선생님, 자바스크립트 지원하지 않는 브라우저는요?

요즘에도 그런 브라우저가 있겠냐만은, 초기 브라우저를 사용하는 유저가 남아 있을 수 있다. 자바스크립트를 지원하지 않는데 어떻게 서비스를 해요? 네, 그래서 자바스크립트를 사용할 수 없을 때 메시지를 남길 수 있는 요소를 제공합니다.

1
2
3
4
5
6
7
8
9
10
11
12
13
<!DOCTYPE html>
<html>
<head>
<title>페이지 제목입니다.</title>
<script type="text/javascript" defer src="example1.js"></script>
<script type="text/javascript" defer src="example1.js"></script>
</head>
<body>
<noscript>
<p>해당 브라우저는 자바스크립트를 지원하지 않습니다. 브라우저 업데이트 이후에 다시 시도해 주세요.</p>
</noscript>
</body>
</html>

<noscript> 요소를 사용하면 간단하게 해결할 수 있다. 스크립트가 활성화된 브라우저에서는 절대 표시되지 않는다.


어쩌란 말이냐

자바스크립트는 외부 파일로 정의하여 사용하는 것을 권장한다. 이유는 다음과 같다.

  1. 관리하기 쉽다.
    코드를 HTML 여기저기 뿌리는 것보다 directory 하나에 모으는 것이 관리에 더 용이하다.
  2. 캐싱이 된다.
    서로 다른 페이지에서 같은 파일을 사용한다면 js 파일은 한 번만 내려받기 때문에 페이지 로딩 시간이 줄어든다.


이 포스트의 모든 내용은 프론트엔드 개발자를 위한 자바스크립트 프로그래밍(인사이트) 책을 참고하여 작성되었습니다.




  1. XHTML 문서에서는 defer=“defer” 형식으로 써야 한다. ↩︎

  2. XHTML 문서에서는 async=“async” 형식으로 써야 한다. ↩︎

Share