iPhone 에서 OAuth 라이브러리 사용하기

지난 주에 아이폰에 OAuth 컨슈머 라이브러리 돌리는데 삽질을 너무 많이 해서 반성하는 의미로 포스팅 해본다. http://oauth.net에 있는 라이브러리는 아이폰에 바로 쓸 수 없어서 약간 손을 봐야하는데 누군가 이미 해놓은 것도 있지만 기본(?) 라이브러리로 한번 해봤다. 붙이는건 그렇게 어렵지 않은데 아이폰에 써드파티 바이너리 프레임웍 추가 안되는거랑 Security.framework 내용이 Mac의 것과 다르다는 걸 몰라서 시간을 엄청 허비했음.

  1. OAuthConsumer 라이브러리를 체크아웃 한다.

    svn checkout http://oauth.googlecode.com/svn/code/obj-c/ .

  2. 프레임웍으로 빌드해서 넣으면 깔끔하겠지만 아이폰에는 그렇게 넣을 수 없으니 소스를 직접 넣는다. 다운받은 OAuthConsumer 디렉토리 아래에서 필요한 파일만 남기고 모두 삭제한다.

    rm -rf English.lproj OAuthConsumer.xcodeproj *.plist *.pch *.rb *Test.?

  3. Xcode에서 OAuthTest 라는 이름의 View-Based Application 하나를 생성한다.

  4. Finder에서 OAuthConsumer 디렉토리를 끌어다 Groups & Files 창의 Classes 아래에 놓는다. 파일을 복사할꺼니까 끌어다 놓을때 뜨는 'Copy items into destination group's folder'에 체크하고 Add 한다.

  5. 이 상태에서 빌드를 해보면 OAToken_KeychainExtensions.m 파일에서 에러가 난다. 원래 Mac Cocoa 환경이라면 Security.framework 라이브러리를 추가해서 컴파일 할 수 있지만 아이폰용 Security.framework 라이브러리는 맥용과 달라서 OAToken_KeychainExtensions.m 파일을 컴파일 시킬 수 없다. 하지만 이 파일은 꼭 필요한건 아니고 나중에 OAuth 인증 끝나고 토큰과 시크릿을 키체인에 안전하게 보관할 수 있게 도와주는 유틸리티인데 필요하면 알아서 구현하고 일단 지워도 문제 없다. 파일 목록에서 OAToken_KeychainExtensions.? 파일을 삭제하고 빌드하면 일단 문제없이 컴파일이 될 것이다.

  6. 시작하기 전에 OAuthConsumer.h 파일을 열어서 import 경로를 올바른 경로로 바꾸어주자.

    #import <Foundation/Foundation.h> #import <OAuthConsumer/OAToken.h> #import <OAuthConsumer/OAConsumer.h> #import <OAuthConsumer/OAMutableURLRequest.h> ...

    이걸 아래처럼 변경.

    #import <Foundation/Foundation.h> #import "OAToken.h" #import "OAConsumer.h" #import "OAMutableURLRequest.h" ...

  7. 이제 OAuthTestViewController.xib 파일을 열어서 아래 그림처럼 웹뷰, 'Get Request Token' 버튼, 'Get Access Token' 버튼, PIN 번호를 입력받을 텍스트 필드가 있는 화면을 생성한다. 'Get Request Token' 버튼을 누르면 Request Token을 얻어와서 트위터의 Authorize URL로 이동시키고, 사용자가 로그인 한 후 보여지는 PIN 번호를 넣고 'Get Access Token' 버튼을 누르면 Access Token을 가져올 것이다.

  8. 위에서 추가한 웹뷰, 텍스트필드의 아웃렛 변수와 두 버튼에 연결될 액션 메서드를 만들고 연결한다.

    #import <UIKit/UIKit.h> @interface OAuthTestViewController : UIViewController { UIWebView *webView; UITextField *textField; } @property (nonatomic, retain) IBOutlet UIWebView *webView; @property (nonatomic, retain) IBOutlet UITextField *textField; - (IBAction)requestTokenButton:(UIButton *)sender; - (IBAction)accessTokenButton:(UIButton *)sender; @end

  9. 먼저 'Get Request Token' 버튼을 눌렀을때 Request Token을 얻어와서 로그에 찍어보자. 아래처럼 호출하도록 requestTokenButton: 메서드를 작성하고 성공/에러시에 호출될 델리게이트 메서드도 만든다.

    #import "OAuthConsumer.h" ... - (IBAction)requestTokenButton:(UIButton *)sender { OAConsumer *consumer = [[OAConsumer alloc] initWithKey:@"Z0DxPl4q7kmSOgh3LTpV4Q" secret:@"LWryiOYBAHJ58PX9Yn1yG5bzDwpMJiksqpXxfst7kcU"]; NSURL *url = [[NSURL alloc] initWithString:@"http://twitter.com/oauth/request_token"]; OAMutableURLRequest *request = [[OAMutableURLRequest alloc] initWithURL:url consumer:consumer token:nil realm:@"http://twitter.com/" signatureProvider:nil]; [request setOAuthParameterName:@"oauth_callback" withValue:@"oob"]; OADataFetcher *fetcher = [[OADataFetcher alloc] init]; [fetcher fetchDataWithRequest:request delegate:self didFinishSelector:@selector(requestTokenTicket:didFinishWithData:) didFailSelector:@selector(requestTokenTicket:didFailWithError:)]; [consumer release]; [url release]; [request release]; [fetcher release]; } - (void)requestTokenTicket:(OAServiceTicket *)ticket didFinishWithData:(NSData *)data { if (ticket.didSucceed) { NSString *responseBody = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]; OAToken *token = [[OAToken alloc] initWithHTTPResponseBody:responseBody]; NSLog(@"Request Token: key=%@, secret=%@", [token key], [token secret]); [token release]; [responseBody release]; } else { NSLog(@"Finish but did not succeed."); } } - (void)requestTokenTicket:(OAServiceTicket *)ticket didFailWithError:(NSError *)error { NSLog(@"Error: %@", [error localizedDescription]); }

    위와 같이 작성해서 실행해보면 requestTokenTicket:didFailWithError: 쪽으로 떨어지면서,

    Operation could not be completed. (NSURLErrorDomain error -1012.)

    이런 메시지가 떨어진다. 이유는,

    [request setOAuthParameterName:@"oauth_callback" withValue:@"oob"];

    이 부분 때문인데 oauth_callback 이라는 파라미터를 추가하고 싶어서 이렇게 적었으면 이 파라미터를 포함하여 시그니쳐를 생성해야 하는데 OAuthConsumer 라이브러리에서는 추가된 파라미터를 제외하고 시그니처를 생성해 요청했고 결과적으로 트위터에서 시그니처가 틀리다는 이유로 200 OK가 떨어지지 않는 상태이다(버그이거나 OAuth 1.0a 스펙을 고려하지 않아서인 듯). 추가된 파라미터를 포함하여 시그니처를 생성하도록 OAMutableURLRequest.m 파일을 수정해보자. 파일을 열어서 _signatureBaseString 메서드 중간쯤에,

    ... for (OARequestParameter *param in [self parameters]) { [parameterPairs addObject:[param URLEncodedNameValuePair]]; } for(NSString *parameterName in [[extraOAuthParameters allKeys] sortedArrayUsingSelector:@selector(compare:)]) { [parameterPairs addObject:[[OARequestParameter requestParameterWithName:parameterName value:[extraOAuthParameters objectForKey:parameterName]] URLEncodedNameValuePair]]; } NSArray *sortedPairs = [parameterPairs sortedArrayUsingSelector:@selector(compare:)]; NSString *normalizedRequestParameters = [sortedPairs componentsJoinedByString:@"&"]; ...

    이렇게 for 루프를 하나 추가한다. 이제 다시 실행해서 'Get Request Token' 버튼을 눌러보면,

    2010-03-05 17:09:40.438 OAuthTest[1691:207] Request Token: key=wyGw0VUSE79MTuVm0iqs7ZdWiPI3ZRJWCZ2k6P73w, secret=AUGrkHfx3nr6xb9Q5dUbNQzykZQvFJ62WW90BojT8

    콘솔에 이렇게 찍히면서 정상적으로 토큰을 얻어올 수 있다.

  10. 이제 Request Token을 얻어왔으니 토큰을 임시로 저장하고 트위터의 Authorize URL을 호출한다. 아래처럼 OAuthTestViewController.h 파일을 수정하고,

    #import <UIKit/UIKit.h> @class OAServiceTicket; @class OAToken; @interface OAuthTestViewController : UIViewController { UIWebView *webView; UITextField *textField; OAToken *requestToken; } @property (nonatomic, retain) IBOutlet UIWebView *webView; @property (nonatomic, retain) IBOutlet UITextField *textField; @property (nonatomic, retain) OAToken *requestToken; ...

    아래처럼 OAuthTestViewController.m 파일을 수정한다.

    if (ticket.didSucceed) { NSString *responseBody = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]; OAToken *token = [[OAToken alloc] initWithHTTPResponseBody:responseBody]; NSLog(@"Request Token: key=%@, secret=%@", [token key], [token secret]); self.requestToken = token; [token release]; [responseBody release]; NSString *authorizeURL = [[NSString alloc] initWithFormat:@"http://twitter.com/oauth/authorize?oauth_token=%@", [self.requestToken.key URLEncodedString]]; [self.webView loadRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:authorizeURL]]]; [authorizeURL release]; } ...

    이제 실행하고 'Get Request Token' 버튼을 누르면 아래 이미지 처럼 인증을 요구하는 화면이 나오고 Allow 하고 나면,

    아래 이미지 처럼 PIN 번호가 보여진다.

  11. 이제 PIN 번호를 입력하고 'Get Access Token'을 클릭했을 때의 처리를 하면 된다. accessTokenButton: 메서드를 아래처럼 작성하고 accessTokenTicket:didFinishWithData:, accessTokenTicket:didFailWithError: 델리게이트 메서드도 만들자.

    - (IBAction)accessTokenButton:(UIButton *)sender { OAConsumer *consumer = [[OAConsumer alloc] initWithKey:@"Z0DxPl4q7kmSOgh3LTpV4Q" secret:@"LWryiOYBAHJ58PX9Yn1yG5bzDwpMJiksqpXxfst7kcU"]; NSURL *url = [[NSURL alloc] initWithString:@"http://twitter.com/oauth/access_token"]; OAMutableURLRequest *request = [[OAMutableURLRequest alloc] initWithURL:url consumer:consumer token:self.requestToken realm:@"http://twitter.com/" signatureProvider:nil]; [request setOAuthParameterName:@"oauth_verifier" withValue:self.textField.text]; OADataFetcher *fetcher = [[OADataFetcher alloc] init]; [fetcher fetchDataWithRequest:request delegate:self didFinishSelector:@selector(accessTokenTicket:didFinishWithData:) didFailSelector:@selector(accessTokenTicket:didFailWithError:)]; [consumer release]; [url release]; [request release]; [fetcher release]; } - (void)accessTokenTicket:(OAServiceTicket *)ticket didFinishWithData:(NSData *)data { if (ticket.didSucceed) { NSString *responseBody = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]; OAToken *token = [[OAToken alloc] initWithHTTPResponseBody:responseBody]; NSLog(@"Got Access Token [key:%@, secret:%@]", token.key, token.secret); [token release]; [responseBody release]; } else { NSLog(@"Finish but did not succeed."); } } - (void)accessTokenTicket:(OAServiceTicket *)ticket didFailWithError:(NSError *)error { NSLog(@"Error: %@", [error localizedDescription]); }

  12. 이제 실행해서 PIN 번호를 넣고 'Get Access Token' 버튼을 누르면 아래처럼 Access Token 정보가 콘솔에 출력된다.

    Got Access Token [key:14368376-CyPcPg7uVLcOkzRJBlJLMVKqZQMzCMQnRxHMmzQG8, secret:HY3eENZ6Pt4AFdUUtzAROlZDaKHOJHtcc7lMKMyKE]

  13. 이제 위에서 출력되는 Access Token 정보를 저장해서 OAMutableURLRequest 클래스로 요청 할 때 token 인자에 넣어 보내면 된다. 요청 할 때 파라미터를 세팅해야 할 경우에는, OARequestParameter 파라미터를 NSArray 로 묶어 OAMutableURLRequest 생성 후에 setParameter: 해주면 된다.

틀린 내용이 있다면 지적해주세요!

'컴퓨터 얘기 > 프로그래밍' 카테고리의 다른 글

iPhone 에서 OAuth 라이브러리 사용하기  (7) 2010/03/05
Read Me 플러그인  (3) 2007/12/07
드림위버와 이별하기  (5) 2007/11/28
MySQL Foreign Key 바보짓  (6) 2007/04/09
TinyMCE 플러그인 - WikiExporter  (5) 2007/02/07
멜론 앨범 커버 다운로더  (20) 2007/02/04

MySQL Foreign Key 바보짓

DROP TABLE IF EXISTS testChild;
DROP TABLE IF EXISTS testParent;

CREATE TABLE testParent (
    id INT NOT NULL,
    PRIMARY KEY(id)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

CREATE TABLE testChild (
    id INT NOT NULL,
    parentId INT DEFAULT NULL,
    PRIMARY KEY(id),
    KEY parentId(parentId),
    CONSTRAINT testFKey FOREIGN KEY(parentId) REFERENCES testParent(id)
        ON DELETE SET NULL ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8;

INSERT INTO testParent VALUES(1);
INSERT INTO testChild VALUES(1, 1);

ALTER TABLE testChild MODIFY parentId INT NOT NULL;

DELETE FROM testParent WHERE id = 1;

MySQL 5.0에서는 마지막 DELETE문을 실행할때 mysql이 crash 되고 4.1에서는 testChild 테이블에 (1, 0) 값이 남게 돼 foreign key constraint가 깨지게 된다. 아놔 이자식 때문에 반나절을 삽질했;;

'컴퓨터 얘기 > 프로그래밍' 카테고리의 다른 글

Read Me 플러그인  (3) 2007/12/07
드림위버와 이별하기  (5) 2007/11/28
MySQL Foreign Key 바보짓  (6) 2007/04/09
TinyMCE 플러그인 - WikiExporter  (5) 2007/02/07
멜론 앨범 커버 다운로더  (20) 2007/02/04
Crizin.HTTPRequest.php  (8) 2007/02/03

TinyMCE 플러그인 - WikiExporter

회사에서 생성되는 문서의 많은 부분은 Trac의 위키로 관리된다. 장점이 많지만 문서의 길이가 길어지기 시작하면 위키 코드만 보고는 편집하기 어려운 것도 사실이다. 좀 분량이 되는 문서를 Google Docs에서 만들었다가 위키로 옮길 일이 있어 예전에 만들다 말았던 위키도우미;;를 끄집어내 TinyMCE 플러그인으로 만들었는데 어지간히 복잡한 문서 말고는 그럭저럭 나와주는 것 같다. 덕분에 집에 일찍 갔다-_-

다운로드 : WikiExporter.1.0.zip (6.02KB)

그림에 보이는 것 처럼 원본은 Google Docs나 드림위버나 MS워드같은 HTML 편집이 가능한 곳에서 작성하고 TinyMCE 편집화면에 붙여넣은 후 왼쪽 위에 있는 빨간 W 버튼을 누르면 HTML 코드를 변환해준다. 문서가 지나치게 길면 컴퓨터가 폭발할 수도 있으니 주의..

TinyMCE를 다운로드 받아 플러그인을 설치해서 써도 되고 (어디 업로드 하지 않고 그냥 PC에서 바로 실행해도 된다) 귀찮은 사람은 이 쪽을 이용해도 된다.

'컴퓨터 얘기 > 프로그래밍' 카테고리의 다른 글

드림위버와 이별하기  (5) 2007/11/28
MySQL Foreign Key 바보짓  (6) 2007/04/09
TinyMCE 플러그인 - WikiExporter  (5) 2007/02/07
멜론 앨범 커버 다운로더  (20) 2007/02/04
Crizin.HTTPRequest.php  (8) 2007/02/03
preg 계열 함수들의 버그?  (10) 2006/08/21

멜론 앨범 커버 다운로더

앞선 Crizin.HTTPRequest.php의 활용 예.

D2 재생모습

D2에서는 각 MP3 파일마다 같은 이름을 가진 JPG 이미지를 넣어놓으면 노래를 재생할때 옆에 같이 보여주는데 멜론 인기곡 Top100 같은걸 다운받아 넣고 각 앨범 커버를 손으로 하나씩 넣어주자면 굉장한 노가다를 해줘야 한다. 이 과정을 간단히 줄여주는 스크립트가 바로 이 녀석.

다운로드 : melon.zip (2.11MB)

압축풀고 auto.bat(이 파일명 정말 좋아;;)를 실행하면 covers 디렉토리를 만들고 오늘의 차트 종합순위 Top100에 해당하는 앨범 커버를 다운로드 한다. 에픽 하이-17-Fan.jpg 같은 이름으로 만들어주기 때문에 대부분의 경우는 멜론에서 받은 DCF 파일이 들어있는 곳에 같이 넣어주기만 하면된다. 가끔씩 에픽 하이-17-Fan.jpg 처럼 트랙번호가 어긋나는 경우가 있는데 멜론 앨범정보가 이상하게 들어있어서 이건 어쩔 수 없음. 몇개 안되니 손으로 고쳐주자;; 또 타이푼-01-기다릴게....jpg 처럼 제목이 마침표로 끝나는 경우에는 D2에서 제대로 앨범 커버 인식을 못하는 것 같으니 DCF, JPG 양쪽 모두 ...을 제거해줘야 한다.

오늘의 Top100이 아니고 주간, 월간 차트의 곡을 받고싶거나 종합순위 말고 가요, 팝 등의 개별 장르 차트를 다운로드 하고 싶으면 src 디렉토리의 melon.php 파일을 메모장으로 열어 앞부분을 약간 수정해줘야 한다.

melon.php 수정화면

공장 출하값(..)은 오늘의 종합차트로 맞춰져있고 이걸 월간 클래식 차트로 바꾸고 싶다면 8번째줄 맨 앞에다 //를 넣어주고 10번째의 //를 제거하고 같은 방법으로 14번째줄에 //를 추가, 19번째줄의 //를 제거하면 된다.

php.exe도 포함돼있고 해서 거시기한 문제가 될 수도 있으니 다른곳으로의 펌/업로드는 삼가해주시기를..

'컴퓨터 얘기 > 프로그래밍' 카테고리의 다른 글

MySQL Foreign Key 바보짓  (6) 2007/04/09
TinyMCE 플러그인 - WikiExporter  (5) 2007/02/07
멜론 앨범 커버 다운로더  (20) 2007/02/04
Crizin.HTTPRequest.php  (8) 2007/02/03
preg 계열 함수들의 버그?  (10) 2006/08/21
IE 6.0의 버그들  (7) 2006/08/11

Crizin.HTTPRequest.php

예전에 웹브라우저를 에뮬레이트 하는 간단한 PHP 클래스를 만든적이 있었는데 회사에 들어온 뒤 파파챠님이 만드신 태터툴즈용 HTTPRequest 클래스에 감명을 받아;; 전체적인 모습을 그 것과 비슷하게 발전시켜왔다. 2년넘게 이걸로 다양한 짓거리들을 하며 써오고 있는데 마지막 버전업이 작년 여름인걸 보니 이제 될건 다 되겠다 싶어 공개. Snoopy같은 라이브러리와 많이 비슷한데 필요한 기능들을 집어넣다보니 꽤 다르게 됐다. 이걸 가지고 할 수 있는 일은 A 게시판을 RSS로 만들어 구독한다던가 B 갤러리에 새 사진이 등록되면 하드에 저장한다던가 브라우저로는 접근하기 어려운 C 사이트의 뒷구멍으로 뭔가를 날리는 등등의 다양한 노가다성 작업이 가능하다.

다운로드

Download from GoogleCode

Simple tutorial

<?
    require 'Crizin.HTTPRequest.php';

    // Create instance
    $h = new HTTPRequest('www.foo.com');
    // Turn on debug mode (request/response streams will be print)
    $h->debug(true);
    // Setting 'PATH'
    $h->setPath('/');
    // Request by GET method
    $h->send();
    // Get responsed informations
    $responseText = $h->responseText;
    $contentType = $h->getResponseHeader('Content-Type');

    // Let's try to another host into 8080 port
    $h->open('www.bar.com', 8080);
    // Path and GET parameter string
    $h->setPath('/accept.php?mode=login&and=more');
    // Send around proxy server
    $h->setProxy('www.proxy.com', 8888);
    // Modify 'User-Agent' header
    $h->setRequestHeader('User-Agent', 'Gozilla/1.0');
    // Import from cookie string
    $h->importCookie('COOK1=foo; COOK2=bar;');
    // Set cookie
    $h->setCookie('cook', 'something');
    // Request by POST method
    $h->send('param1=value1&param2=value2');
    // Get cookie
    $sessionId = $h->getCookie('PHPSESSID');

    // Download image
    $h->setPath('/images/logo.gif');
    // Login with apache authorization
    $h->authorization('myId', 'myPassword');
    // Hide 'User-Agent' header
    $h->removeRequestHeader('User-Agent');
    // Response content will be saved in './save'
    $h->saveToFile('./save');

    // Upload some files
    $h->setPath('/write.php');
    // <input type="file" name="image" value="/files/blah.gif"/> and rename to 'myImage.gif'
    $h->attachFile('image', './files/blah.gif', 'myImage.gif');
    // Request
    $h->send();

    // Test some text exists in $responseText or not
    $result = $h->existText('OK') ? 'Succeed' : 'Failed';
    // Get all text fragments was surrounded by '<td>' and '</td>' (array will be return)
    $result = $h->getAllTextFragments('<td>', '</td>');
    // Get 5th text only (string will be return)
    $result = $h->getTextFragment('<td>', '</td>', 5);
?>

'컴퓨터 얘기 > 프로그래밍' 카테고리의 다른 글

TinyMCE 플러그인 - WikiExporter  (5) 2007/02/07
멜론 앨범 커버 다운로더  (20) 2007/02/04
Crizin.HTTPRequest.php  (8) 2007/02/03
preg 계열 함수들의 버그?  (10) 2006/08/21
IE 6.0의 버그들  (7) 2006/08/11
태터툴즈 1.0.5 플러그인  (58) 2006/05/09

preg 계열 함수들의 버그?

preg_match('/(.)*/', str_repeat('x', 20000), $matches);

PHP에서 위 명령을 실행하면 $matches 변수에 아래와 같은 값이 들어가야 정상이지만,

array(2) {
   [0]=>
   string(20000) "xx...xx"
   [1]=>
   string(1) "x"
}

Segmentation fault를 내고 죽어버리는 경우가 있다. 이유는 아직 이해불가; 20000번의 매치 과정중 두번째 원소에 계속 x를 저장하는 과정에서 메모리가 빵꾸나는게 아닐까 하는 생각이 들지만 캡쳐기능이 없는 괄호 (?:.)*를 사용해봐도 역시 죽어버린다. ereg 계열 함수는 제대로 실행이 되는걸 보면 preg 함수가 삽질하고 있는게 맞는 것 같다. preg_replace(), preg_match_all() 등 모든 함수에서 동일한 결과가 나오며 PHP 4.4.1, 5.1.4에서 이런 증상을 보였다.

좀 복잡하다 싶은 정규식은 극한 상황의 테스트를 꼭 해볼 것;

'컴퓨터 얘기 > 프로그래밍' 카테고리의 다른 글

멜론 앨범 커버 다운로더  (20) 2007/02/04
Crizin.HTTPRequest.php  (8) 2007/02/03
preg 계열 함수들의 버그?  (10) 2006/08/21
IE 6.0의 버그들  (7) 2006/08/11
태터툴즈 1.0.5 플러그인  (58) 2006/05/09
태터툴즈 방문자 그래프 플러그인  (9) 2006/03/22

태터툴즈 1.0.5 플러그인

태터툴즈 1.0.5 릴리즈에 맞추어 만든 플러그인 4종세트.. 당연히 1.0.5 이상에서만 동작하며 각 플러그인들의 라이선스는 GPL에 따르니 더 좋게 고쳐서 나눠쓰세요..;

로봇의 방문횟수 제외 [Download - ExcludeRobotsCounter.zip]

기능
많이 알려진 로봇의 이름을 미리 입력해서 로봇이 방문했을때는 방문자 카운터를 증가시키지 않는다.
설명
플러그인 관리자 화면에서 플러그인을 활성화 시키면 동작한다. 봇의 이름을 추가하거나 삭제할때는 index.php 파일을 열어 $robots 배열에 봇의 이름을 편집해주면 된다. 추후에 User-agent 필터링 기능이 추가되기 전까지 임시로 사용되는 플러그인.

피드버너 리다이렉터 [Download - FeedBurnerRedirector.zip]

기능
태터툴즈의 RSS 주소로 접속하면 피드버너의 피드 주소로 이동시켜준다. 스킨의 [##_rss_url_##] 치환자도 피드버너의 URL로 바뀐다.
설명
사용하는 블로그 식별자가 crizin 이라면 http://feeds.feedburner.com/crizin 주소로 이동된다. 블로그 식별자와 피드버너 ID가 다른 경우에는 index.php 파일 10번째줄의 "http://feeds.feedburner.com/{$blog['name']}" 부분을 "http://feeds.feedburner.com/xxxxxx" 같이 변경해줘야 한다. 피드버너 설정에서 Original Feed 주소는 http://crizin.net/rss 같이 원래 RSS 주소를 입력해두면 된다.

전체피드 읽어오기 [Download - GetEntireFeed.zip]

기능
네이버의 모든 블로그, 이글루스의 블로그중 피드 부분공개를 선택한 블로그에 대해 본문 전체를 보여준다.
설명
플러그인을 활성화 시키면 피드가 업데이트 될때마다 직접 블로그에 접속해 본문을 읽어와 RSS의 본문 대신 저장하게 된다. 따라서 피드 업데이트 속도가 느려질 수 있으며 특이한 스킨을 사용하는 이글루스 블로그에 대해서는 본문을 제대로 읽어오지 못할 가능성도 있다.
주의
부분공개된 피드의 전문을 강제로 읽어와 리더에 저장하는건 블로거의 의도에 반하는 행동이 될 수 있다. 개인적인 편의가 아닌 다수에게 서비스를 제공하는 블로그에서 이 플러그인을 사용하는건 문제의 소지가 될 수 있음에 주의할 것.
변경내역
1.0.1 - 네이버의 글에서 이미지에 달려있는 onload 이벤트를 제거해서 스크립트 오류가 뜨지 않게 함
1.0.2 - 파란의 RSS도 지원 (포스트 하나 가져오려면 두번 접속을 해야해서 매우 느림)
1.0.3 - 네이버 블로그 출력부분 변경사항 반영
1.0.4 - 파란 블로그 출력부분 변경사항 반영
1.0.5 - 네이버 블로그 출력부분 변경사항 반영, 이글루스 포스트는 무조건 읽어오도록 수정

리퍼러 로그 정리 [Download - RefererURLBeautifier.zip]

기능
통계보기 » 리퍼러 통계를 봅니다 메뉴에서 리퍼러 로그를 읽기 쉽게 바꿔주고 검색어가 포함된 경우 검색어를 눈에 잘 띄게 표시해 준다.
설명
리퍼러를 저장하는 공간(255bytes)의 제약으로 인해 매우 긴 URL의 경우 한글이 깨지는 등의 문제가 있을 수 있다. 그리고 index.php 파일의 15번째줄 맨 앞의 //를 제거하면 각 도메인의 favicon을 불러다 표시해준다.
변경내역
1.0.1 - Eolin.com 검색어 표시가 안되는 문제 수정
1.0.2 - Baidu.com 검색어 표시가 안되는 문제 수정
1.0.3 - %uXXXX 형식의 문자 해석해서 보여주도록 수정
1.0.4 - http://images.google.co.kr 등에서 유입되는 검색어가 제대로 추출되지 않는 문제 수정

블로그에서 푸시푸시를..;

며칠전 미니위니에서 본 navyism님의 푸시푸시를 보고 흉내내서 만들어본 물건..

여기 왼쪽 MORE 메뉴 안에 푸시푸시;;를 누르면 실행된다. 맵만들기 귀찮아서 일단 10판까지만 입력하고 그림도 대충 훔쳐다 붙여다 놓음.. 여기까지 만들고 나니 왠지 귀찮아져서 일단 중단;; 나중에 시간남아돌때 맵이나 만들어야지..

push.zip

소스가 궁금한분이 계실까?;;


맵만들기는 소스보면 대충 눈에 보임. 맵에 사용된 문자들은 맘에드는걸로 바꿔도 상관 없음. $size는 정사각형 셀의 크기.. 맵 데이터에 오류가 있을때는 어떻게 동작할지 모름;