2012-07-22 33 views

Trả lời

12

Tập hợp các slide trên loa sàn đưa ra một cái nhìn tổng quan ngắn gọn:

đang middleware Express từ các slide:

var createDomain = require('domain').create; 

app.use(function(req, res, next) { 
    var domain = createDomain(); 

    domain.on('error', function(err) { 
    // alternative: next(err) 
    res.statusCode = 500; 
    res.end(err.message + '\n'); 

    domain.dispose(); 
    }); 

    domain.enter(); 
    next(); 
}); 
+4

Bạn đã thử nghiệm điều này chưa? Nó không hoạt động đối với tôi và domain.enter không có giấy tờ trên trang web của nút. –

+0

Tính năng này có hiệu quả đối với tôi. Tôi không biết tại sao domain.enter lại không có giấy tờ. –

+3

Tôi nên thêm Tôi lo ngại rằng mã này gọi domain.enter nhưng không có miền tương ứng.exit. Có vẻ như một sự rò rỉ có thể xảy ra. –

5

Tôi đã có may mắn thay thế cổ phiếu

var app = express.createServer(); 

với:

var domainCreate = require('domain').create; 
var app = express.createServer(function (req, res, next) { 
    var domain = domainCreate(); 
    domain.run(next); 
}); 

Sau đó, trong middleware của bạn, bạn có thể thêm các thuộc tính để process.domain hoặc thêm xử lý lỗi bổ sung.

+1

Đây có thể là câu trả lời hay tại một thời điểm, nhưng 'express.createServer' không được dùng nữa. – Jess

+0

mục đích của việc này là gì nếu bạn không xử lý lỗi cụ thể cho tên miền đó? –

12

CẬP NHẬT: Cách tiếp cận được mô tả bên dưới đã được triển khai trong mô-đun connect-domain NodeJS, có thể được sử dụng trong các ứng dụng Connect hoặc Express.

Kể từ Express 3, express.createServer không được chấp nhận và cuộc gọi lại của nó sẽ được chuyển đổi thành phần mềm trung gian. Trong phần mềm trung gian, điều quan trọng là thêm đối tượng yêu cầu và kết quả vào miền yêu cầu để các lỗi do chúng xử lý được xử lý bởi trình xử lý lỗi miền.

middleware của tôi trông giống như sau:

var domain = require('domain'); 

app.use(function(req, res, next) { 
    var requestDomain = domain.create(); 
    requestDomain.add(req); 
    requestDomain.add(res); 
    requestDomain.on('error', next); 
    requestDomain.run(next); 
}); 

Bạn có thể tránh thêm các yêu cầu và đáp ứng với một miền yêu cầu nếu bạn gọi http.createServer từ bên trong một miền cấp cao nhất, nhưng các tài liệu tên miền dường như chỉ ra rằng tên miền yêu cầu là phương pháp hay nhất.

Lưu ý rằng mã ở trên không thực hiện bất kỳ hành động nào làm sạch tên miền, chẳng hạn như buộc phải xử lý miền yêu cầu. Thay vào đó, middleware của tôi chọn để chuyển lỗi thông qua ngăn xếp phần mềm trung gian để được xử lý bằng phần mềm trung gian xử lý lỗi cụ thể sau này. YMMV.

+0

Điều này không bảo vệ chống lại các ngoại lệ được ném trong libs của bên thứ 3 ... :( – Jess

+0

@Jess, tôi thừa nhận rằng việc xử lý lỗi ở đây là ngây thơ, nhưng tôi tò mò về những gì bạn đang nhìn thấy. và được cung cấp như là một đối số "lỗi" cho ngăn xếp, giả sử các trình xử lý của bạn có một. –

+0

Tôi đang sử dụng phần tiếp theo sẽ ném một ngoại lệ nếu mệnh đề where không có cú pháp hợp lệ chẳng hạn. o 'emit' thay vì 'ném'. Tôi đã thử tất cả các giải pháp được liệt kê ở đây và dường như không có lỗi nào bị bắt. – Jess

2

Đây là câu trả lời trễ nhưng hãy xem mô-đun express-domain-moddleware. Nó sẽ tự động tạo một tên miền mới cho mỗi yêu cầu. Miền hoạt động có thể được tham chiếu bởi process.domain trong các tuyến đường của bạn. Dưới đây là một ví dụ:

//with domain-middleware 
app.use(require('express-domain-middleware')); 
app.use(app.router); 

app.use(function errorHandler(err, req, res, next) { 
    console.log('error on request %d %s %s: %j', process.domain.id, req.method, req.url, err); 
    res.send(500, "Something bad happened. :("); 
    if(err.domain) { 
    //you should think about gracefully stopping & respawning your server 
    //since an unhandled error might put your application into an unknown state 
    } 
}); 

app.get('/error', function(req, res, next) { 
    db.query('SELECT happiness()', process.domain.intercept(function(rows) { 
    fs.readFile('asldkfjasdf', process.domain.intercept(function(contents) { 
     process.nextTick(process.domain.intercept(function() { 
     throw new Error("The individual request will be passed to the express error handler, and your application will keep running."); 
     })); 
    })); 
    })); 
}); 
+0

Tôi upvoted này bởi vì 'express-domain-middleware' trông giống như câu trả lời tốt nhất (và vẫn được duy trì) cho câu hỏi này. Cùng với 'node-ok' của cùng một tác giả trông giống như một giải pháp mạnh mẽ để xử lý lỗi trong nút/express. Tôi sẽ thêm một liên kết khác cũng liên quan đến cùng một chủ đề: cách phản hồi lỗi khi chúng bị bắt: https://github.com/hapijs/boom –

0

Các lĩnh vực hiện đang bị phản đối trong nút:

https://nodejs.org/api/domain.html

Đối với mục đích của 'lỗi quy hoạch', tôi đã tạo ra một thư viện cho phép bạn viết không đồng bộ mã theo cách tốt đẹp: https://github.com/vacuumlabs/yacol. Một trong những lợi ích của nó là bạn có thể có hành vi giống như miền với một ngữ nghĩa rất hay; kiểm tra nó ra!

Các vấn đề liên quan