2012-07-24 28 views
22

Ben http://eng.wealthfront.com/2011/12/converting-dynamic-svg-to-png-with.htmlPNG Sunucu tarafına SVG - kullanan node.js

Bağlantı tam (node.js kullanarak) bir PNG sunucu tarafı bir d3.js SVG Vis dönüştürme bu öğretici izlemeye çalışıyorum kod: Ben bu b olası nedenlerini

/Users/me/Node/node_modules/jsdom/lib/jsdom.js:171 
     features = JSON.parse(JSON.stringify(window.document.implementation._fea 
                  ^
    TypeError: Cannot read property 'implementation' of undefined 
     at exports.env.exports.jsdom.env.processHTML (/Users/dereklo/Node/node_modules/jsdom/lib/jsdom.js:171:59) 
     at Object.exports.env.exports.jsdom.env (/Users/dereklo/Node/node_modules/jsdom/lib/jsdom.js:262:5) 
     at Server.<anonymous> (/Users/dereklo/Node/Pie/pie_serv.js:26:9) 
     at Server.EventEmitter.emit (events.js:91:17) 
     at HTTPParser.parser.onIncoming (http.js:1785:12) 
     at HTTPParser.parserOnHeadersComplete [as onHeadersComplete] (http.js:111:23) 
     at Socket.socket.ondata (http. 

bilen var mı sayfam yüklemek için bir istek yapmak girişiminde zamanhttps://gist.github.com/1509145

Ancak, bu hatayı almaya devam e? Jsdom modülünü iyice kurdum, bu yüzden bu sorunlara neyin neden olduğunu bilmiyorum ... şimdiden teşekkürler.

DÜZENLEME

Bu benim node.js sunucusu uygulamak için kullanıyorum kodudur. Benim son sayısı son sayısı

var http = require('http'), 
    url = require('url'), 
    jsdom = require('jsdom'), 
    child_proc = require('child_process'), 
    w = 400, 
    h = 400, 
    __dirname = "Users/dereklo/Node/pie/" 

    scripts = ["/Users/dereklo/Node/pie/d3.min.js", 
       "/Users/dereklo/Node/pie/d3.layout.min.js", 
       "/Users/dereklo/Node/pie/pie.js"], 
     //scripts = ["./d3.v2.js", 
     //   "./d3.layout.min.js", 
      //  "./pie.js"] 

    htmlStub = '<!DOCTYPE html><div id="pie" style="width:'+w+'px;height:'+h+'px;"></div>'; 

http.createServer(function (req, res) { 

    res.writeHead(200, {'Content-Type': 'image/png'}); 
    var convert = child_proc.spawn("convert", ["svg:", "png:-"]), 
     values = (url.parse(req.url, true).query['values'] || ".5,.5") 
     .split(",") 
     .map(function(v){return parseFloat(v)}); 

    convert.stdout.on('data', function (data) { 
    res.write(data); 
    }); 
    convert.on('exit', function(code) { 
    res.end(); 
    }); 

    jsdom.env({features:{QuerySelector:true}, html:htmlStub, scripts:scripts, done:function(errors, window) { 
    var svgsrc = window.insertPie("#pie", w, h, values).innerHTML; 

    console.log("svgsrc",svgsrc); 

    //jsdom's domToHTML will lowercase element names 
    svgsrc = svgsrc.replace(/radialgradient/g,'radialGradient'); 
    convert.stdin.write(svgsrc); 
    convert.stdin.end(); 
    }}); 
}).listen(8888, "127.0.0.1"); 

console.log('Pie SVG server running at http://127.0.0.1:8888/'); 
console.log('ex. http://127.0.0.1:8888/?values=.4,.3,.2,.1'); 

... Bu kaynaktan altındadır

events.js:66 
     throw arguments[1]; // Unhandled 'error' event 
        ^
Error: This socket is closed. 
    at Socket._write (net.js:519:19) 
    at Socket.write (net.js:511:15) 
    at http.createServer.jsdom.env.done (/Users/dereklo/Node/Pie/pie_serv.js:38:19) 
    at exports.env.exports.jsdom.env.scriptComplete (/Users/dereklo/Node/node_modules/jsdom/lib/jsdom.js:199:39) 
+0

Bize bazı kodları gösterebilir misiniz? :-) –

+1

Tam anlamıyla eğitim kodunu kopyalayıp yapıştırdım .... – Apollo

+0

@FlorianMargaine Eğiticinin özüne bir link ekledim. Bu Florian'ta bir çatlak almak ister misin? – Apollo

cevap

49

Bu çıkar eğer sorunuzun yararlı bir cevap olarak kanıtlamak olduğunu olabilir "node.js kullanarak" şart. Eğer size yardımcı olmazsa, belki daha sonra ziyaretçiler onu ilginç bulacaktır.

Aynı sorunu (sunucu tarafı d3 rasterleştirmeyi) çözmek için bir süredir çalışıyorum ve en iyi çözüm olarak PhantomJS buldum.

server.js:

var page = require('webpage').create(), 
    renderElement = require('./renderElement.js'), 
    Routes = require('./Routes.js'), 
    app = new Routes(); 

page.viewportSize = {width: 1000, height: 1000}; 
page.open('./d3shell.html'); 

app.post('/', function(req, res) { 
    page.evaluate(new Function(req.post.d3)); 
    var pic = renderElement(page, '#Viewport'); 
    res.send(pic); 
}); 

app.listen(8000); 

console.log('Listening on port 8000.'); 

Routes.js: https://gist.github.com/3061477
renderElement.js:

<!DOCTYPE HTML> 
<html> 
<head> 
    <title>Shell</title> 
</head> 
<body> 
    <div id="Viewport" style="display: inline-block"></div> 
    <script src="http://cdnjs.cloudflare.com/ajax/libs/d3/2.8.1/d3.v2.min.js" type="text/javascript"></script> 
</body> 
</html> 

Daha sonra başlayabilirsiniz: gibi görünmelidir https://gist.github.com/3176500

d3shell.html phantomjs server.js ve POST d3 = [ViewView] oluşturan [d3 kodu] ile sunucu ve er taban64 kodlu bir png ile cevap verecektir.

(PhantomJS 1.7 veya üstü gerektirir.)

+0

BSD-2 lisansı nedeniyle fantom kullanamazsınız, ancak bu çok fazla zaman harcadığınız harika bir gönderiye benziyor. Umarım başkalarına yardımcı olur ... – Apollo

+2

Tam bir çalışma örneği gönderir misiniz? Nasıl veya ne "post" yapmalıyım emin değilim. – reubano

+0

Ayrıca bu örnek kullanmaya çalışıyorum ama @anubano gibi, bahsettiğin gibi nasıl yayınlayacağının farkında değilim. Ben phantomJS için yeniyim. Teşekkürler – zed

İlgili konular