c/fe

http://d.hatena.ne.jp/uzulla から移行しました。

mixiアプリで、IDの仕様が変わったから変換するって作業

すっごい放置してたんだけど、もう月末には締切だよ!って感じなので対応をしたね!

概要

どこにもズバリズバズバな説明が書いて無いからなかなか弱ったんだけど、


opensocial_owner_idは前は数字やったけど、こんどは英数字13文字になるから!*1変換してよ!一対一で差し替えるだけだから!」


というそれだけの話でしたね。いやそれだけの話なのに、HOWTOみたいなのが記載ないってどういうことや。(俺だけだったのかなあ…、一発で分からなかったの)

具体的な作業

とりあえずアプリ設定画面にいって、変換API叩くよーって申請すると新IDを引く為の用意ができるから、
手元にあるであろうopensocial_owner_idをキーにして、すっごいガンガンAPI叩いて、対応する新IDを取得していく。
APIにアタック^H^H^Hクセスする速度は特に注意書きされてなかったので、ウェイトとかいれなかった!
そんで全部とれたら、既存のopensocial_owner_idと差し替えて、再度アプリ設定画面にいって、変換作業おわったよーってボタンを押す。
すると完了やで!

さらに具体的なツール(二度と使わないけど、メモ)

YAPC直後でPerl熱が高まっているので、Perlで書きましたね。
Prepared Statementで名前付きプレースホルダつかいたかってんけど、
普段使ってる ゆるふわPDOとはちょっと書き方ちがったので、面倒で?、?って感じですね。


ーー
DBのスキーマ的には
userという名前のテーブルがあって、
id <= 連番
owner_id <= opensocial_owner_idでとれるやつ
new_owner_id <= 新しく差し替えるopensocial_owner_idをALTERで追加しとく
という想定。

あ、new_owner_idは、後述しますけどひけない事が大量にあるので、Uniqueは後でかけたほうがいいでしょうね。
引けなかったデータを捨てるか、整合性の為にうめごろしするかは自由かなと。


ーー

#!/usr/bin/perl
use 5.0.8;
use strict;
use warnings;
use JSON::XS;
use OAuth::Lite;
use OAuth::Lite::Consumer;
use DBI;

#mixisetting
my %options = (
	site            => 'api.mixi-platform.com',
	consumer_key    => 'xxxxxxxxxxxxxxxxxxxxxx',
	consumer_secret => 'xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx',
	requester_id    => '0000000000', #アプリオーナーのowner_id
);

my $consumer = OAuth::Lite::Consumer->new(
	consumer_key    => $options{consumer_key},
	consumer_secret => $options{consumer_secret}
);


my $db = DBI->connect('dbi:mysql:database=db_name', 'db_user', 'db_pass',{
	mysql_enable_utf8 => 1,
});


my $st = $db->prepare('SELECT * FROM user ORDER BY id');
$st->execute();
my $update_puid = $db->prepare('UPDATE user SET new_owner_id = ? WHERE id= ? ');

while(my $row = $st->fetchrow_hashref ){

	my $id = $row->{id};
	my $owner_id = $row->{owner_id};
	print "id-> $id, owner_id-> $owner_id, ";

	my $response = $consumer->request(
	    method  => 'GET',
	    url     => sprintf('http://%s/os/0.8/people/'.$owner_id.'/@self', $options{site}),
	    params  => {
			xoauth_requestor_id => $options{requester_id},
			fields=>'platformUserId',
	    });

	if ($response->is_success) {
		my $data = JSON::XS::decode_json($response->decoded_content);
		print "new_owner_id->".$data->{entry}->{platformUserId};
		$update_puid->execute($data->{entry}->{platformUserId}, $id);
	} else {
		warn $response->status_line;
		print "GET ERROR";
	}

	print "\n";
}
$db->disconnect;

この取得がおわったら、
・アプリを適当にメンテ中表示にでもして(弱小アプリならしなくたってバレないだろうけど)
・ALTERでnew_owner_idとowner_idいれかえて
・管理画面で変換作業完了を押して
・アプリをメンテ中表示外す
(・古いowner_idは適当にのこしておくか、消す)
という感じですね。




作業自体は簡単だったんだけど

俺の設計で、速度とかの問題からowner_idをスーパークッキー代わりにしてるところがあったんだけど、それがこの仕様変更で死んだ、仕方ない…。


後、変換プログラムで引けないデータが結構大量にでてびっくりするけど、これはアプリを削除してるからってことらしい。
これの弊害として、通常アプリを再インストール(?)したとき、しれっと既存データもどせるけど、残念なことに今後は突き合わせできないから、この時点でアプリアンインストールしてる人はどうしてもロストということになるんだろうな。

*1:実際には、今後はIDをアプリ間で共有できないとか、色々仕様が