NOMO.asia

티스토리에 추가된 블로그 구독 기능

2019년 3월 20일, 티스토리에 블로그 구독이라는 기능이 추가되었다.

여타 사이트의 구독 or 팔로잉 기능과 비슷하게, 마음에 드는 블로그를 구독하여 글을 쉽고 빠르게 모아볼 수 있는 기능이다.

자세한 설명은 다음의 링크 참조. https://notice.tistory.com/2477?category=110385


블로그 구독 버튼은 티스토리 관리자 페이지의 [메뉴바/구독 설정] 에서 활성화 할 수 있다.

이 블로그는 해당 기능이 나오자 마자 바로 블로그 구독 버튼을 활성화 해주었다.



블로그 구독 버튼 활성화 후 SyntaxHighlighter 가 작동하지 않는 증상 발생

그런데 블로그 구독 버튼을 활성화 한 후 3일 만에 알게된 것인데,

SyntaxHighlighter 가 적용되지 않고 원본 텍스트로만 출력되는 증상이 발생하고 있었다.

내 환경에서만 이런 문제가 발생하는 것인지는 따로 테스트를 해보지 않아서 잘 모르겠다.


내 경우 CDN 을 통해 SyntaxHighlighter 3.0.83 을 불러와 <pre> 태그를 이용하는 방법으로 SyntaxHighlighter 를 사용하고 있고

블로그 스킨으로는 개인적으로 수정한 Custom 스킨을 사용하고 있다.



문제 원인 파악

Chrome의 개발자도구를 열어 문제를 확인했다.



SyntaxHighlighter 의 shCore.js 에서 재귀호출이 너무 많이 일어나 오류가 발생하고 있었다.


CDN 에서 불러오는 shCore.js 파일은 압축(minify)되어있어 분석이 쉽지 않으므로

minify되지 않은 XRegExp.js 파일과 shCore.js 을 로드했다. (CDN 에서 불러오는 shCore.js 는 두 파일이 합쳐진 형태이다.)




이후 다시 문제를 확인하자 아래의 그림과 같이

구독 버튼을 추가하기위해 로드된 menubar.min.js 에서 String.replace 함수를 호출하는 과정에서 에러가 시작되었다고 한다.

그리고 그 에러는 XRegExp.js 로 연결되어 있었다.




XRegExp 라이브러리는 정규표현식을 편하게 사용할 수 있도록 돕고,

브라우저와 상관없이 동일한 정규표현식 동작을 수행할 수 있도록 호환성을 제공하는 라이브러리 이다.



설명에 따르면 아래와 같이 정규표현식을 사용하는데 쓰이는 몇가지 함수들이 브라우저 간 차이를 보이는 부분이 있어

호환성을 유지할 수 있도록 이러한 함수들을 덮어씌우는 동작이 있다고 한다.


그래서 아래의 그림과 같이 몇가지 prototype 함수들을 real 이라는 Object 에 복사해두고




아래의 그림과 같이, 브라우저 간 호환성을 유지할 수 있도록 수정된 함수를 덮어씌운다.

함수 내에서는 real 에 복사된 함수를 다시 호출하고, 조건식에 따라 브라우저 간 호환성 유지를 위한 여러 동작을 수행한다(고한다).




그리고 menubar.min.js 에서는 String.prototype.replace 함수를 호출하는데,

이 때 SyntaxHighlighter 를 사용하는 경우라면 XRegExp 에서 덮어씌워진 수정된 함수를 불러오게 된다.

여기서 에러(재귀호출)가 발생한다.




여기까지만 보고 코드를 더 분석해보지는 않았지만 대충 원인을 추정해보자면,


모종의 이유로 real 에 복사된 함수가 한 번 더 덮어씌워지게 되는 경우

수정된 함수 내에서는 real 에 복사된 함수를 호출하고 있으므로 결국 자기 자신을 호출하는 것이 되어 재귀호출이 발생할 수 있을 것 같다.


아니면 그냥 그 외 라이브러리 충돌 문제로 재귀호출이 발생하게 되어 문제가 발생하게 된 것일 수도 있다.

자세하게 분석하지는 않아서 정확한 이유는 모르겠다.


이 외에도 비슷한 몇가지 문제가 있었다.



임시로 문제 해결하기

XRegExp 코드에 작성된 설명에 따르면, 함수를 덮어씌우는 부분은 브라우저 간 호환성을 위한 것이고
SyntaxHighlighter 에서 사용하고 있는 XRegExp 라이브러리의 버전은 1.5.0 으로 2010년에 나온 꽤 오래된 것이었다.
따라서 현대 브라우저들에서는 문제가 발생되는 부분을 그냥 다 지워버려도 호환성 문제가 발생하지 않을 것으로 추정했다.

문제가 되는 부분들을 다 지워버리고 테스트 해본 결과 IE 11, Chrome 73, Firefox 66 에서 문제 없이 동작함을 확인했다.
일단 내가 SyntaxHighlighter 를 사용하는 수준에서는 문제가 발생하지 않았지만, 오래된 브라우저나 특정 환경에서 에러가 발생할 수도 있을 것같다.


혹시나 이 방법을 시도해볼 사람은 아래와 같이 하면 된다.

일단 아래의 두 파일(regExp_new.js, shCore_new.js)을 다운받는다.
SyntaxHighlighter 3.0.83 버전의 코드를 Github 에서 다운받아 작업했다.
XRegExp_new.js 파일은 앞서 설명한 문제가 될만한 부분을 삭제한 파일이고
shCore_new.js 파일은 별도의 수정은 하지 않았지만, XRegExp 와 shCore 가 합쳐진 것과 구분하기 위해 올려놨다.

[티스토리 블로그 관리] - [스킨 편집] - [html 편집] 으로 들어간다.




파일 업로드 버튼을 누른 뒤



추가 버튼을 눌러 위에서 다운받은 두 파일(regExp_new.js, shCore_new.js)을 업로드한다.



이후 HTML 버튼을 눌러 HTML 편집창으로 간 뒤

기존의 shCore.js 를 불러오는 부분을 아래와 같이 수정한다.





혹시 기존에도 shCore.js 와 XRegExp.js 를 모두 로드하고 있었던 경우 두 라인을 모두 주석처리 해주면 된다.
주의할 점은 regExp_new.js 를 불러오는 라인이 shCore_new.js 를 불러오는 라인보다 반드시 위에 있어야 한다.

수정을 완료하였으면 적용 버튼을 눌러 저장한다.



근본적인 원인을 찾아서 수정했다면 더 좋았겠지만, 짧은 시간을 들여 해결할 수 있는 수준에서 대충 해치웠다.

사실 이 포스트를 적는 시간이 더 오래 걸렸다.