項目簡介:
NodeJS 作爲服務器,接收前端請求,經過處理轉發對應 Yelp 與 Google API ,返回請求結果。通過此種方式,可避免暴露 API Key,並可在服務器端可翻情況下突破訪問限制。另外,項目使用 Node-Fetch,使用簡單,便於理解。
目錄結構:
|- - - - GoogleYelpTest
|- - - - - - - node_modules
|- - - - - - - server.js
|- - - - - - - package.json
|
|- - - - Client
|- - - - - - - index.html
執行步驟:
npm init
npm install node-fetch --save
npm install express --save
node ./server.js
代碼文件:
package.json
{
"name": "googleyelpapi",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1",
"start": "node ./server.js"
},
"author": "",
"license": "ISC",
"dependencies": {
"express": "^4.16.3",
"node-fetch": "^2.1.2"
}
}
server.js
var fetch = require('node-fetch');
var express = require('express');
var fs = require('fs');
var app = express();
//設置跨域訪問
app.all('*', function(req, res, next) {
res.header("Access-Control-Allow-Origin", "*");
res.header("Access-Control-Allow-Headers", "X-Requested-With");
res.header("Access-Control-Allow-Methods", "PUT,POST,GET,DELETE,OPTIONS");
res.header("X-Powered-By", '3.2.1')
res.header("Content-Type", "application/json;charset=utf-8");
next();
});
// 備註:
// 以下請求均爲 GET 請求
// 請求中的 API Key 出於隱私考慮,使用 [Your Key] 代替
// 每個方法前均兩句用例註釋,上句爲前端請求內容,下句爲 NodeJS 請求相應 API 內容
// "Best Matches"
// localhost:8081/yelp/best_match?name=Gary Danko&city=San Francisco&state=CA&country=US&address1=800 N Point St
// https://api.yelp.com/v3/businesses/matches/best?name=Gary Danko&city=San Francisco&state=CA&country=US&address1=800 N Point St
app.get('/yelp/best_match', function(req, res) {
const query = req.query;
let result = {};
fetch(`https://api.yelp.com/v3/businesses/matches/best?name=${query.name}&city=${query.city}&state=${query.state}&country=${query.country}&address1=${query.address1}`, {
headers: {
'Authorization': 'Bearer [Your Key]'
}
})
.then(res => res.json())
.then(json => res.send(json));
console.log(" YELP BEST MATCH ");
})
// "Yelp Reviews"
// localhost:8081/yelp/WavvLdfdP6g8aZTtbBQHTw/reviews
// https://api.yelp.com/v3/businesses/WavvLdfdP6g8aZTtbBQHTw/reviews
app.get('/yelp/:key/reviews/', function(req, res) {
const query = req.query;
fetch(`https://api.yelp.com/v3/businesses/${req.params.key}/reviews`, {
headers: {
'Authorization': 'Bearer [Your Key]'
}
})
.then(res => res.json())
.then(json => res.send(json));
console.log(" YELP REVIEWS ");
})
// "Google Nearby"
// http://localhost:8081/google/nearby?latGeo=-33.8670522&lonGeo=151.1957362&radius=1000&types=food&keyword=vegetarian&key=[Your Key]
// https://maps.googleapis.com/maps/api/place/nearbysearch/json?location=-33.8670522,151.1957362&radius=1000&types=food&keyword=vegetarian&key=[Your Key]
app.get('/google/nearby', function(req, res) {
const query = req.query;
let distance = (distance | 10) / (0.000621);
fetch(`https://maps.googleapis.com/maps/api/place/nearbysearch/json?location=${query.latGeo},${query.lonGeo}&radius=${distance}&types=${query.types}&keyword=${query.keyword}&key=[Your Key]`)
.then(res => res.json())
.then(json => res.send(json));
console.log(" Google Nearby ");
})
// "Google Nearby Next"
// http://localhost:8081/google/nearby/next?pagetoken=CpQCAgEAAFxg8o-eU7_uKn7Yqjana-HQIx1hr5BrT4zBaEko29ANsXtp9mrqN0yrKWhf-y2PUpHRLQb1GT-mtxNcXou8TwkXhi1Jbk-ReY7oulyuvKSQrw1lgJElggGlo0d6indiH1U-tDwquw4tU_UXoQ_sj8OBo8XBUuWjuuFShqmLMP-0W59Vr6CaXdLrF8M3wFR4dUUhSf5UC4QCLaOMVP92lyh0OdtF_m_9Dt7lz-Wniod9zDrHeDsz_by570K3jL1VuDKTl_U1cJ0mzz_zDHGfOUf7VU1kVIs1WnM9SGvnm8YZURLTtMLMWx8-doGUE56Af_VfKjGDYW361OOIj9GmkyCFtaoCmTMIr5kgyeUSnB-IEhDlzujVrV6O9Mt7N4DagR6RGhT3g1viYLS4kO5YindU6dm3GIof1Q&key=[Your Key]
// https://maps.googleapis.com/maps/api/place/nearbysearch/json?pagetoken=CpQCAgEAAFxg8o-eU7_uKn7Yqjana-HQIx1hr5BrT4zBaEko29ANsXtp9mrqN0yrKWhf-y2PUpHRLQb1GT-mtxNcXou8TwkXhi1Jbk-ReY7oulyuvKSQrw1lgJElggGlo0d6indiH1U-tDwquw4tU_UXoQ_sj8OBo8XBUuWjuuFShqmLMP-0W59Vr6CaXdLrF8M3wFR4dUUhSf5UC4QCLaOMVP92lyh0OdtF_m_9Dt7lz-Wniod9zDrHeDsz_by570K3jL1VuDKTl_U1cJ0mzz_zDHGfOUf7VU1kVIs1WnM9SGvnm8YZURLTtMLMWx8-doGUE56Af_VfKjGDYW361OOIj9GmkyCFtaoCmTMIr5kgyeUSnB-IEhDlzujVrV6O9Mt7N4DagR6RGhT3g1viYLS4kO5YindU6dm3GIof1Q&key=[Your Key]
app.get('/google/nearby/next', function(req, res) {
const query = req.query;
console.log(`https://maps.googleapis.com/maps/api/place/nearbysearch/json?pagetoken=${query.pagetoken}&key=[Your Key]`);
fetch(`https://maps.googleapis.com/maps/api/place/nearbysearch/json?pagetoken=${query.pagetoken}&key=[Your Key]`)
.then(res => res.json())
.then(json => res.send(json));
console.log(" Google Nearby Next ");
})
// "Google Place"
// http://localhost:8081/google/details?placeid=ChIJN1t_tDeuEmsRLIWYxBbGKeA&key=[Your Key]
// https://maps.googleapis.com/maps/api/place/details/json?placeid=ChIJN1t_tDeuEmsRLIWYxBbGKeA&key=[Your Key]
app.get('/google/details', function(req, res) {
const query = req.query;
let result = {};
fetch(`https://maps.googleapis.com/maps/api/place/details/json?placeid=${query.placeid}&key=[Your Key]`)
.then(res => res.json())
.then(json => res.send(json));
console.log(" Google Details ");
})
// "Google Place"
// localhost:8081/google/geocode?address=US&key=[Your Key]
// https://maps.googleapis.com/maps/api/geocode/json?address=US&key=[Your Key]
app.get('/google/geocode', function(req, res) {
const query = req.query;
fetch(`https://maps.googleapis.com/maps/api/geocode/json?address=${query.address}&key=[Your Key]`)
.then(res => res.json())
.then(json => res.send(json));
console.log(" Google Geocode ");
})
// "Google Place"
// localhost:8081/google/photo?maxwidth=400&photoreference=CnRtAAAATLZNl354RwP_9UKbQ_5Psy40texXePv4oAlgP4qNEkdIrkyse7rPXYGd9D_Uj1rVsQdWT4oRz4QrYAJNpFX7rzqqMlZw2h2E2y5IKMUZ7ouD_SlcHxYq1yL4KbKUv3qtWgTK0A6QbGh87GB3sscrHRIQiG2RrmU_jF4tENr9wGS_YxoUSSDrYjWmrNfeEHSGSc3FyhNLlBU&key=[Your Key]
// https://maps.googleapis.com/maps/api/place/photo?maxwidth=400&photoreference=CnRtAAAATLZNl354RwP_9UKbQ_5Psy40texXePv4oAlgP4qNEkdIrkyse7rPXYGd9D_Uj1rVsQdWT4oRz4QrYAJNpFX7rzqqMlZw2h2E2y5IKMUZ7ouD_SlcHxYq1yL4KbKUv3qtWgTK0A6QbGh87GB3sscrHRIQiG2RrmU_jF4tENr9wGS_YxoUSSDrYjWmrNfeEHSGSc3FyhNLlBU&key=[Your Key]
app.get('/google/photo', function(req, res) {
const query = req.query;
fetch(`https://maps.googleapis.com/maps/api/place/photo?maxwidth=1000&photoreference=${query.photoreference}&key=[Your Key]`)
.then(res => {
const dest = fs.createWriteStream(`./image1.png`, {
autoClose: true,
});
res.body.pipe(dest);
});
console.log(" Google Photo ");
})
var server = app.listen(8081, function() {
var host = server.address().address
var port = server.address().port
console.log(" 服務器配置: http://%s:%s", host, port)
})
index.html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>NodeJs 服務器代理</title>
<script src="https://cdn.bootcss.com/jquery/3.3.1/jquery.min.js">
</script>
<script>
$(document).ready(function() {
$("button").click(function() {
// 此處訪問 NodeJS 服務器,參數中無需帶有 API Key
$.get("http://localhost:8081/yelp/best_match?name=Gary Danko&city=San Francisco&state=CA&country=US&address1=800 N Point St", function(data, status) {
$("#status").html("Status: \n" + status);
$("#response").html(JSON.stringify(data));
});
});
});
</script>
</head>
<body>
<div>
<p>發送 HTTP GET 請求, 經由服務器處理並訪問第三方 API, 返回結果</p>
<button>按 鈕</button>
<div>
<p id="status"></p>
<p id="response"></p>
</div>
</div>
</body>
</html>
注意事項:
Yelp,美國最大在線點評網站,國內可訪問
Google Place API,顧名思義,你懂得