רן בר-זיק לפני 8 שנים כ- 4 דקות קריאה
express.js – שימוש ב-API של ה-request | אינטרנט ישראל
במאמר הקודם כיסינו את ה-middleware ברמת האפליקציה וגם הראינו איך משתמשים בארגומנטים ב-URL. במאמר הזה אנו נלמד איך משתמשים ב-API. המאמר הזה נכתב כאשר גרסת ה-API של express היא 4. אבל גם אם אתם קוראים את המאמר הזה בשלב יותר מאוחר, לא אמורה להיות בעיה משמעותית כיוון שאני מסביר כאן על העקרון של ה-API ולא על כל פונקציה ופונקציה.
ראשית, כל ה-API מרוכז באופן מאוד נוח באתר הרשמי של express, אני לא אעבור על כל ה-API אבל על חלקים רלוונטיים מתוכו. את ההסבר אני אדגים על ה-userLoggermiddleware שאותו הראיתי במאמר הקודם. בגדול, כך נראה ה-app.js שלנו שמופעל על ידי node app.js:
var express = require('express');
var app = express();
var help = require('./help');
var user = require('./user');
app.listen(3000, function () {
console.log('Example app listening on port 3000!');
});
app.use('/help', help);
app.use('/user', user);
אפשר לראות שיש לו שני ראוטרים: אחד המוקדש ל-help/X והשני מוקדש ל user/X. הראוטר של user/X נקרא user.js:
var express = require('express');
var router = express.Router();
var userLogger = require('./userLogger');
// using the middleware
router.use('/:id',userLogger);
router.get('/:id', function(req, res) {
res.send('User ' + req.params.id + ' entered the system');
});
module.exports = router;
הראוטר משתמש ב-middleware של userLogger.js – כך הוא נראה:
var userLogger = function (req, res, next) {
console.log('User ID used ' + req.params.id);
next();
};
module.exports = userLogger;
אז בואו ונתחיל, אם אני נכנס ל-URL ומוסיף פרמטרים, כמו למשל http://localhost:3000/user/abu%20lele?param1=aaaa¶m2=bbbb – איך אני יכול לקבל את הפרמטרים? באופן מאוד פשוט:
var userLogger = function (req, res, next) {
console.log(req.query);
next();
};
module.exports = userLogger;
אם אני אסתכל על הקונסולה, אני אראה:
{ param1: 'aaaa', param2: 'bbbb' }
מאיפה ידעתי שיש תכונה של query ב-request? לא משמים אלא מה-API שמתעד את כל התכונות של ה-request, שם אני רואה שיש תכונת query. ה-request הזה זמין בכל מקום: גם בראוטר, גם ב-middleware וגם ב-app עצמו. איפה שיש request, אני יכול לקבל גישה לתכונות שלו. כמובן שחלקן ישתנו עם הקונטקסט, למשל, אם אני אבדוק את ה-path, ב-app אני אקבל את ה-path המלא אבל ב-router (או ב-middleware של ראוטר) אני אקבל את ה-path היחסי לראוטר.
אם למשל אני משתמש ב-middleware כזה:
var userLogger = function (req, res, next) {
console.log('path is ' + req.path);
next();
};
module.exports = userLogger;
תפקידו הוא להדפיס את req.path לקונסולה.
אני משתמש בו ב-app.js
var express = require('express');
var app = express();
var help = require('./help');
var user = require('./user');
var userLogger = require('./userLogger');
app.listen(3000, function () {
console.log('Example app listening on port 3000!');
});
// using the middleware
app.use(userLogger);
app.use('/help', help);
app.use('/user', user);
וגם בראוטר user.js:
var express = require('express');
var router = express.Router();
var userLogger = require('./userLogger');
// using the middleware
router.use(userLogger);
router.get('/:id', function(req, res) {
res.send('User ' + req.params.id + ' entered the system');
});
module.exports = router;
ואני נכנס ל http://localhost:3000/user/abu lele – אז מה לפי דעתכם אקבל בלוג? התשובה היא:
path is /user/abu%20lele
path is /abu%20lele
למה? כי בפעם הראשונה, בקונטקסט של ה-app, הקונטקסט הראשי, אני אקבל את ה-path המלא. בקונטקסט השני, של הראוטר, אני אקבל את ה-path המלא יחסית לראוטר. שהוא user. שימו לב לזה בפעם הבאה שאי קונסיסטנטיות מטריפה אתכם.
יש כמה וכמה תכונות שימושיות ומומלץ להסתכל ב-API כדי לראות את כולן. אפשר גם להדפיס לקונסולה את אובייקט ה-request כדי להציץ.
אין המון מתודות ל-request. המתודה החשובה והעיקרית היא accept שבודקת את ה-headers של הבקשה, הנה דוגמה ליישום שימושי – אצור middleware בשם headerCheckerשירוץ מה-app (כלומר הוא ירוץ על כל הנתיבים). להזכירכם, כך middleware שרץ מה-app נראה. אני קורא ל-headerChecker.js עם ה-require ואז משתמש ב app.use כדי להפעילו:
var express = require('express');
var app = express();
var help = require('./help');
var user = require('./user');
var headerChecker = require('./headerChecker');
app.listen(3000, function () {
console.log('Example app listening on port 3000!');
});
// using the middleware
app.use(headerChecker);
app.use('/help', help);
app.use('/user', user);
headerChecker.js נראה כך:
var headerChecker = function (req, res, next) {
// the order of this list is significant; should be server preferred order
switch(req.accepts()) {
case 'json':
res.setHeader('Content-Type', 'application/json')
break;
case 'html':
res.setHeader('Content-Type', 'text/html')
break;
default:
// the fallback is text/plain, so no need to specify it above
res.setHeader('Content-Type', 'text/plain')
break
}
next();
};
module.exports = headerChecker;
המתודה accept בודקת את ה-Accept HTTP header field של הבקשה ומחזירה טקסט שהוא הדבר הכי תואם לבקשה. כך למשל, אם ה-Accept HTTP header field של הבקשה
הוא text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8, המתודה תחזיר html. במקרה הזה, אני קובע את ה-header של התשובה בהתאם ל-header של הבקשה. את זה אני עושה עם מתודה שנקראת setHeader שהיא מתודה של התשובה, ה-res או ה-response. ועל ה-API של ה-response נדבר במאמר הבא.