custom stream object? (nodejs) - node.js

Is it possible to extend / initialize the require('stream').Stream; object ? I would like to be able to create a stream object that i can push data to and have all the listeners notified when new data arrive.
I tried the following:
var stream = require('stream');
var test = new stream.Stream();
test.write(new Buffer('mads'));
But i get the following error:
TypeError: Object [object Object] has no method 'write'
at repl:1:6
at Interface.<anonymous> (repl.js:168:22)
at Interface.emit (events.js:67:17)
at Interface._onLine (readline.js:153:10)
at Interface._line (readline.js:408:8)
at Interface._ttyWrite (readline.js:585:14)
at ReadStream.<anonymous> (readline.js:73:12)
at ReadStream.emit (events.js:88:20)
at ReadStream._emitKey (tty_posix.js:306:10)
at ReadStream.onData (tty_posix.js:69:12)
at ReadStream.emit (events.js:67:17)

For anyone who stumbles on this question today (node v0.10.x), this can be easily achieved using the PassThrough stream introduced with streams2.
var stream = require('stream');
var test = stream.PassThrough();
test.write('mads');
test.end();

You have to create those methods yourself and also set the writable property to true, and don't forget to emit the events in those methods you override as well so that you can use it as a regular event emitter. Check this question for more information.

Related

Sending bitcoins using bitcoinjs-lib

I'm following tutorial for bitcoinjs at https://medium.com/#orweinberger/how-to-create-a-raw-transaction-using-bitcoinjs-lib-1347a502a3a#.wkf9g2lk0
I receive undefined error for
var key = bitcoin.ECKey.fromWIF("L1Kzcyy88LyckShYdvoLFg1FYpB5ce1JmTYtieHrhkN65GhVoq73");
Reading https://github.com/bitcoinjs/bitcoinjs-lib/issues/487 I use instead
var key = bitcoin.ECPair.fromWIF("L1Kzcyy88LyckShYdvoLFg1FYpB5ce1JmTYtieHrhkN65GhVoq73");
For line : console.log(key.pub.getAddress().toString()); (from tutorial)
I receive similar exception :
TypeError: Cannot read property 'getAddress' of undefined
at repl:1:20
at REPLServer.defaultEval (repl.js:262:27)
at bound (domain.js:287:14)
at REPLServer.runBound [as eval] (domain.js:300:12)
at REPLServer.<anonymous> (repl.js:431:12)
at emitOne (events.js:82:20)
at REPLServer.emit (events.js:169:7)
at REPLServer.Interface._onLine (readline.js:211:10)
at REPLServer.Interface._line (readline.js:550:8)
at REPLServer.Interface._ttyWrite (readline.js:827:14)
'getAddress' method is also deprecated, what to use instead ?
Any other tutorials for sending bitcoins ? They seem difficult to find ?
This should work
var key = bitcoin.ECPair.fromWIF("L1Kzcyy88LyckShYdvoLFg1FYpB5ce1JmTYtieHrhkN65GhVoq73");
var address = key.getAddress().toString()
console.log(address) // 17hFoVScNKVDfDTT6vVhjYwvCu6iDEiXC4
Better still using newer version of bitcoin.js library do
const bitcoin = require('bitcoinjs-lib');
let keyPair = bitcoin.ECPair.makeRandom();
let publicKey = keyPair.publicKey
const { address } = bitcoin.payments.p2pkh({ pubkey: publicKey });
const privateKey = keyPair.toWIF();
console.log(address)
console.log(privateKey)

Redis -nodejs simple program -ERROR

I am getting error for even a simple nodejs redis commands.
This is the error I am getting.
/home/veera/Radha/node_modules/redis-client/lib/redis-client.js:394
var callback = originalCommand[originalCommand.length - 1];
^
TypeError: Cannot read property 'length' of undefined
at Client.onReply_ (/home/veera/Radha/node_modules/redis-client/lib/redis-client.js:394:51)
at maybeCallbackWithReply (/home/veera/Radha/node_modules/redis-client/lib/redis-client.js:143:30)
at ReplyParser.feed (/home/veera/Radha/node_modules/redis-client/lib/redis-client.js:183:29)
at Socket. (/home/veera/Radha/node_modules/redis-client/lib/redis-client.js:337:28)
at Socket.emit (events.js:95:17)
at Socket. (_stream_readable.js:765:14)
at Socket.emit (events.js:92:17)
at emitReadable_ (_stream_readable.js:427:10)
at emitReadable (_stream_readable.js:423:5)
at readableAddChunk (_stream_readable.js:166:9)
And the code is,
var client = require("./redis-node-client/lib/redis-client").createClient();
client.set('test', 'data');
My redis version is ,
redis-server --version
Redis server v=3.0.4 sha=00000000:0 malloc=jemalloc-3.6.0 bits=64 build=4e722bd58502cba0
https://github.com/fictorial/redis-node-client/issues/26 - same issue has been discussed long time back but the version they are discussing is 1.2.
My version is 3.0.4.
Please help me to fix this issue.
It looks like this library is no more supported. ( Description itself says abandoned project.) Unless you have strict requirement, use actively developed and production ready library like node-redis.
Example using node-redis
var client = require("node-redis").createClient();
client.set('test', 'data');
client.get('test',function(err, data){
if(err) console.log(err);
else console.log('reply from redis:' + data);
});
client.quit();

node.js: Cannot read property 'defaultEncoding' of undefined

I wanted to write a changeable write() function.
var write = function(s) {
process.stdout.write(s);
}
write("Hello world!");
I thought you could just write it shorter:
var write = process.stdout.write;
write("Hello world!");
But here I will receive this error:
TypeError: Cannot read property 'defaultEncoding' of undefined
at Writable.write (_stream_writable.js:172:21)
at Socket.write (net.js:613:40)
at repl:1:2
at REPLServer.self.eval (repl.js:110:21)
at Interface.<anonymous> (repl.js:239:12)
at Interface.EventEmitter.emit (events.js:95:17)
at Interface._onLine (readline.js:202:10)
at Interface._line (readline.js:531:8)
at Interface._ttyWrite (readline.js:760:14)
at ReadStream.onkeypress (readline.js:99:10)
Why is that?
It all has to do with how javascript handles this. Inside the function process.stdout.write there is a call to defaultEncoding() using this variable.
In javascript, this is not assigned a value until an object invokes the function where this is defined and it is relative to the calling object.
So in your first example, this points to process.stdout object and it has the method defaultEncoding.
In your second example, this is undefined since the function is being called from the global namespace. When process.stdout.write tries to call defaultEncoding, it will throw the error you mentioned.
You can manually define the this value for a function using Function.prototype.call() method. Example:
var write = process.stdout.write;
write.call(process.stdout, "Hello world!");
The first argument of call is the object to be used as this inside the function.
I recommend reading this article, it explains a lot about this in javascript.
Use the .bind() method, it is designed exactly for your case.
var write = process.stdout.write.bind(process.stdout);
write("Hello world!");
This sets this variable inside the process.stdout.write method to process.stdout.

ForEachLine() in node.js

Referring to slide no 35 in ppt on slideshare
When I run this code
var server = my_http.createServer();
server.on("request", function(request,response){
var chunks = [];
output = fs.createWriteStream("./output");
request.on("data",function(chunk){
chunks = forEachLine(chunks.concat(chunk),function(line){
output.write(parseInt(line,10)*2);
output.write("\n");
})
});
request.on("end",function(){
response.writeHeader(200,{"Content-Type":"plain/text"})
response.end("OK\n");
output.end()
server.close()
})
});
server.listen("8080");
I get error as
chunks = forEachLine(chunks.concat(chunk),function(line){
^
ReferenceError: forEachLine is not defined
Of course I unserstand that I need to include some library but when I googled this I found nothing . Since I am complete newbie to this I have absolutely no idea how to resolve it.
Any suggestions will be appreciable.
EDIT
Using the suggested answer I am getting error as
events.js:72
throw er; // Unhandled 'error' event
^
TypeError: Invalid non-string/buffer chunk
at validChunk (_stream_writable.js:150:14)
at WriteStream.Writable.write (_stream_writable.js:179:12)
at /var/www/html/experimentation/nodejs/first.js:18:20
at Array.forEach (native)
at forEachLine (/var/www/html/experimentation/nodejs/first.js:8:60)
at IncomingMessage.<anonymous> (/var/www/html/experimentation/nodejs/first.js:17:18)
at IncomingMessage.EventEmitter.emit (events.js:95:17)
at IncomingMessage.<anonymous> (_stream_readable.js:736:14)
at IncomingMessage.EventEmitter.emit (events.js:92:17)
at emitReadable_ (_stream_readable.js:408:10)
Thanks
See proxy_stream.js
function forEachLine(chunks, callback) {
var buffer = chunks.join("")
buffer.substr(0, buffer.lastIndexOf("\n")).split("\n").forEach(callback)
return buffer.substr(buffer.lastIndexOf("\n") + 1).split("\n")
}
The link to the repo was on the first slide.
EDIT BY LET's CODE FOR ERROR MESSAGE
Came to know the actual issue now .
I was using nod v0.10 and it is buggy in getting the streams so I was getting the error. Downgraded to v0.8 and same code is working perfect .

Custom REPL in nodejs

I'm trying to play with the nodejs built in REPL from the documentation.
http://nodejs.org/api/repl.html
The example of adding an item is as follows:
repl.start().context.m = msg;
I cant seem to find away to add multiple menus. I've tried doing:
menus = {m = 'hello', f = 'foo'}
repl.start().context = menus
But that doesn't work either. I get:
testREPL> m
TypeError: needs a 'context' argument.
at REPLServer.self.eval (repl.js:113:21)
at Interface.<anonymous> (repl.js:250:12)
at Interface.EventEmitter.emit (events.js:88:17)
at Interface._onLine (readline.js:199:10)
at Interface._normalWrite._line_buffer (readline.js:308:12)
at Array.forEach (native)
at Interface._normalWrite (readline.js:307:11)
at Socket.ondata (readline.js:90:10)
at Socket.EventEmitter.emit (events.js:115:20)
at TCP.onread (net.js:395:14)
Does anybody know how to get this working?
You can't assign to the context property, you have to add properties to it. What you are trying is "overwriting" it with your own object. Try to assign each property by itself instead:
var context = repl.start({}).context;
context.m = 'hello';
context.f = 'foo';

Resources