2012-06-24 37 views
86

Tôi đang cố gắng xây dựng máy chủ web trong node.js sẽ hỗ trợ tập lệnh tên miền chéo, trong khi vẫn cung cấp tệp tĩnh từ một thư mục công cộng. Tôi đang sử dụng express.js và không thực sự chắc chắn cách cho phép viết mã miền chéo (Access-Control-Allow-Origin: *).Cách bật chia sẻ tài nguyên gốc (CORS) trong khung công tác express.js trên node.js

Tôi đã thấy this post, điều mà tôi không thấy hữu ích.

var express = require('express') 
    , app = express.createServer(); 

app.get('/', function (req, res, next) { 
    res.header("Access-Control-Allow-Origin", "*"); 
    res.header("Access-Control-Allow-Headers", "X-Requested-With"); 
    next(); 
}); 

app.configure(function() { 
    app.use(express.methodOverride()); 
    app.use(express.bodyParser()); 
    app.use(app.router); 
}); 

app.configure('development', function() { 

    app.use(express.static(__dirname + '/public')); 
    app.use(express.errorHandler({ dumpExceptions: true, showStack: true })); 
}); 

app.configure('production', function() { 


    var oneYear = 31557600000; 
    // app.use(express.static(__dirname + '/public', { maxAge: oneYear })); 
    app.use(express.static(__dirname + '/public')); 
    app.use(express.errorHandler()); 
}); 

app.listen(8888); 
console.log('express running at http://localhost:%d', 8888); 
+0

Lưu ý app.all vs app.get. TÙY CHỌN OPTIONS không được GET –

+0

xem [local-web-server] (https://github.com/75lb/local-web-server) để biết ví dụ về một nút đơn giản, máy chủ web tĩnh hỗ trợ CORS – Lloyd

+0

xem cho phép- cors.org/server_apache.html để biết thêm thông tin – Mostafa

Trả lời

139

Check-out the example from enable-cors.org:

In your ExpressJS app on node.js, do the following with your routes:

app.all('/', function(req, res, next) { 
    res.header("Access-Control-Allow-Origin", "*"); 
    res.header("Access-Control-Allow-Headers", "X-Requested-With"); 
    next(); 
}); 

app.get('/', function(req, res, next) { 
    // Handle the get for this route 
}); 

app.post('/', function(req, res, next) { 
// Handle the post for this route 
}); 

Cuộc gọi đầu tiên (app.all) nên được thực hiện trước khi tất cả các tuyến đường khác trong ứng dụng của bạn (hoặc ít nhất là những người bạn muốn trở thành CORS kích hoạt).

[Chỉnh sửa]

Nếu bạn muốn tiêu đề xuất hiện cho các tập tin tĩnh là tốt, cố gắng này (chắc chắn rằng nó trước khi cuộc gọi đến use(express.static()):

app.use(function(req, res, next) { 
    res.header("Access-Control-Allow-Origin", "*"); 
    res.header("Access-Control-Allow-Headers", "X-Requested-With"); 
    next(); 
}); 

Tôi thử nghiệm này với mã của bạn và có các tiêu đề trên tài sản từ public thư mục:

var express = require('express') 
    , app = express.createServer(); 

app.configure(function() { 
    app.use(express.methodOverride()); 
    app.use(express.bodyParser()); 
    app.use(function(req, res, next) { 
     res.header("Access-Control-Allow-Origin", "*"); 
     res.header("Access-Control-Allow-Headers", "X-Requested-With"); 
     next(); 
    }); 
    app.use(app.router); 
}); 

app.configure('development', function() { 
    app.use(express.static(__dirname + '/public')); 
    app.use(express.errorHandler({ dumpExceptions: true, showStack: true })); 
}); 

app.configure('production', function() { 
    app.use(express.static(__dirname + '/public')); 
    app.use(express.errorHandler()); 
}); 

app.listen(8888); 
console.log('express running at http://localhost:%d', 8888); 

bạn có thể, tất nhiên, gói chức năng thành một module để bạn có thể làm một cái gì đó như

// cors.js 

module.exports = function() { 
    return function(req, res, next) { 
    res.header("Access-Control-Allow-Origin", "*"); 
    res.header("Access-Control-Allow-Headers", "X-Requested-With"); 
    next(); 
    }; 
} 

// server.js 

cors = require('./cors'); 
app.use(cors()); 
+0

Xin cảm ơn phản hồi của bạn. Tôi đã làm những gì bạn đề xuất (phần đầu tiên, nhưng vẫn không thấy bất kỳ khác nhau trong các tiêu đề yêu cầu) Tôi đã đính kèm mã hiện tại của tôi ở trên. bạn có thể giải thích cách tôi có thể tích hợp phần còn lại của giải pháp của bạn cho điều đó không? – Guy

+1

Tôi ngạc nhiên rằng, vì bạn đang 'use'ing' app.router' trước 'express.static' nên nó không sửa đổi tiêu đề cho các tệp tĩnh; trong mọi trường hợp, tôi đã cập nhật câu trả lời của tôi để nó hoạt động. –

+0

Cảm ơn! Tôi thấy bạn đúng. Các tài sản được lấy từ máy chủ với các tiêu đề được yêu cầu. Tôi có thể chưa hiểu rõ vấn đề thực sự của mình. Tôi đang cố thực hiện cuộc gọi API tới máy chủ bên ngoài bằng lệnh nhận. và đó là nơi tôi gặp lỗi: XMLHttpRequest không thể tải http://www.SOMEURL.com. Nguồn gốc http: // localhost: 8888 không được Access-Control-Allow-Origin cho phép. – Guy

45

Sau giải pháp @Brandon Tilley, dường như nó không có tác dụng với tôi lúc đầu. Bạn không chắc chắn lý do tại sao, có thể tôi đang sử dụng phiên bản chrome và phiên bản khác của nút. Sau khi đã thực hiện một số chỉnh sửa nhỏ, nó hiện đang hoạt động cho tôi.

app.all('*', function(req, res, next) { 
    res.header('Access-Control-Allow-Origin', '*'); 
    res.header('Access-Control-Allow-Methods', 'PUT, GET, POST, DELETE, OPTIONS'); 
    res.header('Access-Control-Allow-Headers', 'Content-Type'); 
    next(); 
}); 

Trong trường hợp ai đó phải đối mặt với vấn đề tương tự như tôi, điều này có thể hữu ích.

+0

Lưu ý app.all vs app.get. Đây là yêu cầu OPTIONS không được GET –

+0

Điều này phù hợp với tôi (Tôi đang tìm nạp đối tượng bằng cách sử dụng Backbone). Tôi đang cố gắng tìm ra nếu nó sẽ làm việc trong IE 8 ... có vẻ như nó nên, nhưng tôi không biết nếu bất cứ điều gì đặc biệt là cần thiết cho điều này "XDomainRequest" điều ... https: //developer.mozilla. org/en-US/docs/HTTP/Access_control_CORS # Browser_compatibility –

+0

Nếu bạn đang làm việc với jQuery, đây là những gì bạn cần. – film42

2

tôi sử dụng này:

var app = express(); 

app 
.use(function(req, res, next){ 
    res.header('Access-Control-Allow-Origin', '*'); 
    res.header('Access-Control-Allow-Headers', 'X-Requested-With'); 
    next(); 
}) 
.options('*', function(req, res, next){ 
    res.end(); 
}) 
; 

h.readFiles('controllers').forEach(function(file){ 
    require('./controllers/' + file)(app); 
}) 
; 

app.listen(port); 
console.log('server listening on port ' + port); 

mã này giả định rằng các bộ điều khiển của bạn đang nằm trong thư mục bộ điều khiển. mỗi tập tin trong thư mục này nên được một cái gì đó như thế này:

module.exports = function(app){ 

    app.get('/', function(req, res, next){ 
     res.end('hi'); 
    }); 

} 
-5

Một bước bổ sung tôi cần để có được để chuyển đổi URL của tôi http://localhost-http://127.0.0.0

+0

Bạn đang đề cập đến điều gì? – Blunderfest

+0

Bạn có nghĩa là http://127.0.0.1 không? Bạn nghĩ nó khác biệt như thế nào? –

1

Đề nghị sử dụng các mô-đun cors nhanh. Điều này cho phép bạn đưa các miền vào danh sách trắng, cho phép/giới hạn các tên miền cụ thể cho các tuyến đường, v.v.,

+0

mô-đun đó có thể cho phép bạn gọi dịch vụ từ http: // localhost /? – SuperUberDuper

8

Hãy thử các mô-đun cors npm này.

var cors = require('cors') 

var app = express() 
app.use(cors()) 

Module này cung cấp nhiều tính năng để CORS tinh chỉnh thiết lập như danh sách trắng miền, cho phép CORS cho apis cụ thể, vv

0

Bạn phải thiết lập Access-Control-Allow-Credentials: true, nếu bạn muốn sử dụng "cookie" qua "Credentials"

app.all('*', function(req, res, next) { 
    res.header('Access-Control-Allow-Origin', '*'); 
    res.header('Access-Control-Allow-Credentials', true); 
    res.header('Access-Control-Allow-Methods', 'PUT, GET, POST, DELETE, OPTIONS'); 
    res.header('Access-Control-Allow-Headers', 'Content-Type'); 
    next(); 
}); 
Các vấn đề liên quan