バイナリオブジェクトをredisに保存して、画像として提供しようとしています。
データを保存するために使用しているコードは次のとおりです。
var buff=new Buffer(data.data,'base64');
client.set(key,new Buffer(data.data,'base64'));
データをダンプするコードは次のとおりです。
client.get(key,function(err,reply){
var data = reply;
response.writeHead(200, {"Content-Type": "image/png"});
response.end(data,'binary');
});
データの最初の数バイトが破損しているようです。マジックナンバーが間違っています。
いくつかの実験をしました:
私が次のことをするとき:
var buff=new Buffer(data.data,'base64');
console.log(buff.toString('binary'));
私はこれを得る:
0000000:c289 504e 470d 0a1a 0a00 0000 0d49 4844
私がこれをするとき
var buff=new Buffer(data.data,'base64');
console.log(buff);
私は次のようになります:
バッファ8950 4e 47 0d 0a 1a 0a 00 00 00 0d 49 48 44 52 00 00 00
C2がどこから来ているのかわかりません
問題は、NodeのRedisクライアントがデフォルトで応答をJavaScript文字列に変換することです。
クライアントの作成時にreturn_buffers
オプションをtrue
に設定することで、これを解決しました。
var client = redis.createClient(7000, '127.0.0.1', {'return_buffers': true});
詳細については、 ここ を参照してください。
バイナリ文字列を格納する方法を理解できませんでした。
これが私の回避策です:
ここで、dataはbase64文字列のデータです
client.set(count,data);
データを提供するには:
client.get(last,function(err,reply){
var data = reply;
response.writeHead(200, {"Content-Type": "image/png"});
var buff=new Buffer(data,'base64');
response.end(buff);
});
毎回変換を行う必要があるため、これは理想的ではありませんが、機能しているようです。
return_buffers
の問題は、純粋なバッファデータを使用していない場合、他のバッファを文字列に変換するために何かを行う必要があることです。 detect_buffers
はオプションかもしれませんが、信頼性が低すぎます。
余分な計算サイクルを気にしない場合。また、試すことができます:
// convert your buffer to hex string
client.set(key, mybuffer.toString('hex'));
// create a new buffer from hex string
client.get(key, function (err, val) {
var bin = new Buffer(val, 'hex');
});
私にとってうまくいったのは、Buffer
の場合はdata.toString('binary')
を使用することです。また、それをutf-8
としてだけでなく、binary
として再解釈しないようにしてください。
この記事は、これを行うことの意味を説明するトピックで見つけました。この記事を読む前に、(プログラミング言語に関係なく)読むことを強くお勧めします。
http://qnimate.com/storing-binary-data-in-redis/
要約すると、Redisはメモリ内のキー/値ストアであるため、使用可能なメモリをすぐに使い果たしてRedisインスタンスのパフォーマンスを低下させるため、画像などの潜在的に大きな値をRedis内に保存しないことをお勧めします。ファイル自体ではなく、ファイルの場所をRedisに保存することをお勧めします。