약간의 잡담
또 업데이트가 불가피한 마지막 날까지 미루게 되었네요. 지난주에 사실 내용이 꽤 많았는데 정말 움직이기 싫더라고요. 안드로이드 미니 게임을 만들며 많은 문제에 부딪혔고, 해결하고 나니 또 새로운 문제가 터졌습니다. 버그를 해결하던 중 신기한 것을 발견했는데, 바로 만델브로 집합(Mandelbrot Set)입니다. (지구 반대편의 어떤 형씨도 안드로이드 Canvas 성능 문제로 골머리를 앓았었나 보네요...)
아주 예쁜 GIF가 하나 있어서 여기 올리려 했는데, 용량이 너무 커서(26MB) 링크로 대신합니다: http://7xl5fb.com1.z0.glb.clouddn.com/mandelbrot.gif
1. 방안 선택
위챗 공중 플랫폼의 에디터가 지난번 업데이트(2015-11-20) 이후 사용성이 완전히 사라졌습니다. 예쁜 레이아웃을 원한다면 서드파티 온라인 에디터를 빌려야 할 정도죠. 구독 계정을 만들 때 자동 동기화를 고려했었는데, 개인 계정은 인증을 안 해주고 API도 개방하지 않아 무산된 적이 있습니다.
API 권한 없이 편의를 도모하려면 3가지 선택지가 있습니다:
-
서드파티 플랫폼에 위탁
-
비공개 API 사용 (로그인 시뮬레이션 등...)
-
블로그 포스트를 기반으로 도문 메시지 생성 (이후 수동 복사 및 붙여넣기)
위탁은 돈이 들어서 고려하지 않았고, 비공개 API는 오랫동안 고민했지만 불안정하고 가용 리소스가 적어 구현에 시간이 오래 걸릴 것 같아(Time is money, my friend) 포기했습니다. 대신 유용한 몇 가지를 찾았습니다:
- 워드프레스 플러그인 wechat_subscribers
특징: 최신 글 자동 회신, 랜덤 글, 검색 결과 등, 영구 무료.
주소: https://github.com/Soopro/wechat_subscribers
- 워드프레스 플러그인 Wechat-Manager
특징: 키워드 자동 회신 최신 글, 주/월/년 단위 최다 댓글 글, 글 검색 결과.
주소: https://github.com/9IPHP/Wechat-Manager
- Node로 래핑된 Wechat API
특징: 공식 API보다 사용성이 좋을 것입니다 (Jackson Tian의 기여도가 70.2%나 되니까요).
주소: https://github.com/node-webot/wechat-api
앞의 두 워드프레스 플러그인은 기능은 강력하지만 도문 메시지 편집 문제를 해결해주지는 못했습니다. wechat_subscribers는 가능할지도 모르겠지만, 결국 다른 플러그인을 발견해서 시도를 멈췄습니다.
추천하는 것은, 아주 눈에 띄지 않는(스타 1개는 방금 제가 누른 겁니다) 워드프레스 플러그인입니다:
- WP_wechat_text_generator
소개: 위챗 공식 계정용 포스트를 생성할 수 있는 워드프레스 플러그인.
주소: https://github.com/nervouna/WP_wechat_text_generator
2. DIY
저는 워드프레스 플러그인을 직접 작성해본 적이 없어서 찾아보며 고치느라 좀 느렸지만 할 만했습니다. 소스 코드를 받자마자 본 것은 라이선스였습니다:
* License: WTFPL
*
* DO WHATEVER THE FUCK YOU WANT, PUBLIC LICENSE
* TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
*
* 0. You just DO WHATEVER THE FUCK YOU WANT.
참 흥미로운 작가더군요. 관심 있다면 그의 홈페이지를 구경해 보세요: IGNORE THE BLUEPRINT
구체적인 수정 과정은 굳이 말하지 않겠습니다. 그리 영광스러운 일은 아니니까요 (원작자는 PM인데, JS를 보고 알았습니다). 두 가지 까다로운 문제에 부딪혔습니다.
1. Markdown
플러그인이 포스트 내용을 가져온 뒤 행별로 explode하여 '<p>'.row.'</p>'로 출력하더군요. 제 블로그 글은 마크다운 형식이어서 다음과 같이 전처리가 필요했습니다:
// markdown transform
$wechat_item_content = apply_filters('the_content', $wechat_item_content);
위 코드는 범용적입니다. Node의 event.emit('the_content')와 유사하게, 블로그 내용을 처리하려는 모든 플러그인의 관련 함수를 호출합니다. 예를 들어 마크다운 플러그인에서는 다음과 같이 처리합니다:
add_filter('the_content', 'Markdown', 6);
add_filter('the_content', 'balanceTags', 50);
2. 사용자 정의 CSS
스타일 수정은 필수였습니다. 플러그인 스타일이 너무 단순했고, code, pre 같은 개발자 전용 태그에 대한 미화가 없었거든요. 스타일 수정은 JS를 통해 구현되었으며 구조는 다음과 같습니다:
function refineStyle() {
// h2~h5
var h2s = post.getElementsByTagName('h2');
for (var i = h2s.length - 1; i >= 0; i--) {
// .entry-content h2 { font-size: 18px; padding-left: 13px; margin: 20px 0; }
h2s[i].style.fontSize = '18px';
h2s[i].style.margin = '20px 0';
h2s[i].style.background = '#66b3ff';
h2s[i].style.padding = '4px 0';
h2s[i].style.paddingLeft = '13px';
h2s[i].removeAttribute('class');
};
// ...
}
document.addEventListener('DOMContentLoaded', function() {
refineStyle();
selectText('wechat-post');
});
대략 이런 뜻입니다. 구현 방식이 예쁘지는 않지만(cssText로 리팩토링 가능), 방법은 꽤 교묘합니다. PHP로 포스트 내용을 파싱해서 인라인 스타일을 채우려 했다면... 생각만 해도 끔찍하네요. 리팩토링 후는 이렇습니다:
// table
var tables = post.getElementsByTagName('table');
for (var i = tables.length - 1; i >= 0; i--) {
// .entry-content table, .comment-content table { border-bottom: 1px solid #ededed; color: #757575; font-size: 12px; line-height: 2; margin: 0.8em; margin-top: 0; width: 100%; }
tables[i].style.cssText = 'border-bottom: 1px solid #ededed; color: #757575; font-size: 12px; line-height: 2; margin: 0.8em; margin-top: 0; width: 100%;';
tables[i].removeAttribute('class');
//!!! 注意要去掉w, h
tables[i].removeAttribute('width');
tables[i].removeAttribute('height');
};
cssText를 쓰니 훨씬 편하고, CSS를 인라인 스타일로 변환하기에도 용이했습니다.
3. 기타 문제
크롬에서 문제가 있습니다. 글 생성 후 selectText로 전체 선택하여 Ctrl+C로 위챗 에디터에 붙여넣으면 스타일이 엉망이 됩니다. (주의: 온라인 미리보기에서는 괜찮아 보이지만, 휴대폰으로 미리보기를 보내면 스타일이 많이 사라진 것을 볼 수 있습니다.) selectText의 구체적인 구현은 다음과 같습니다:
function selectText(containerid) {
var text = document.getElementById(containerid);
// IE
if (document.body.createTextRange) {
var range = document.body.createTextRange();
range.moveToElementText(text);
range.select();
} else {
// others
var selection = window.getSelection();
var range = document.createRange();
range.selectNodeContents(text);
selection.removeAllRanges();
selection.addRange(range);
}
}
여기저기 뒤져봤지만 성과가 없었고, selectText 방법 자체에는 문제가 없었습니다. 그래서 결국 Firefox(FF) 사용을 권장하기로 했습니다.
P.S. 사실 크롬에서도 자동 선택된 내용을 취소하고 마우스로 직접 전체 선택해서 복사하면 제대로 작동합니다. 둘의 차이가 무엇인지 모르겠네요.
클립보드 자동 복사도 고려해봤는데, 호환성 문제(특히 크롬)가 까다로운 것 같아 그만두었습니다.
아직 댓글이 없습니다