Academic Integrity: tutoring, explanations, and feedback — we don’t complete graded work or submit on a student’s behalf.

Use NPM to download a free module called “ moment ” described in our textbook an

ID: 3873830 • Letter: U

Question

Use NPM to download a free module called “moment” described in our textbook and use Node.js built-in “fs” module to log the customer feedback messages to a text file named “feedback.log”. Each feedback has to be logged on its own line and has to be started with a time stamp in a pair of square brackets.

app.js

/**

app.js

This is a simple web site that hosts

a fake Wake Tech Credit Union web site.

It is used to demonstrate how easy it is to

create and deploy a web sever using Node.js.

*/

var moment = require('./node_modules/moment');

var express = require('express');

var fs = require('fs');

/**

* Define the sample application.

*/

var SampleApp = function() {

// Scope.

var self = this;

/* ================================================================ */

/* Helper functions. */

/* ================================================================ */

/**

* Set up server IP address and port # using env variables/defaults.

*/

self.setupVariables = function() {

// Set the environment variables we need.

//self.ipaddress = process.env.IP;

//self.port = process.env.PORT || 5000;

//if (typeof self.ipaddress === "undefined") {

// self.ipaddress = "127.0.0.1";

//};

};

/**

* Populate the cache.

*/

self.populateCache = function() {

if (typeof self.zcache === "undefined") {

self.zcache = { 'index.html': '' };

}

// Local cache for static content.

self.zcache['index.html'] = fs.readFileSync('./index.html');

};

/**

* Retrieve entry (content) from cache.

* @param {string} key Key identifying content to retrieve from cache.

*/

self.cache_get = function(key) { return self.zcache[key]; };

/**

* terminator === the termination handler

* Terminate server on receipt of the specified signal.

* @param {string} sig Signal to terminate on.

*/

self.terminator = function(sig){

if (typeof sig === "string") {

console.log('%s: Received %s - terminating sample app ...',

Date(Date.now()), sig);

process.exit(1);

}

console.log('%s: Node server stopped.', Date(Date.now()) );

};

/**

* Setup termination handlers (for exit and a list of signals).

*/

self.setupTerminationHandlers = function(){

// Process on exit and signals.

process.on('exit', function() { self.terminator(); });

// Removed 'SIGPIPE' from the list - bugz 852598.

['SIGHUP', 'SIGINT', 'SIGQUIT', 'SIGILL', 'SIGTRAP', 'SIGABRT',

'SIGBUS', 'SIGFPE', 'SIGUSR1', 'SIGSEGV', 'SIGUSR2', 'SIGTERM'

].forEach(function(element, index, array) {

process.on(element, function() { self.terminator(element); });

});

};

/* ================================================================ */

/* App server functions (main app logic here). */

/* ================================================================ */

/**

* Create the routing table entries + handlers for the application.

*/

self.createRoutes = function() {

self.routes = { };

self.routes['/feedback'] = function(req, res) {

console.log("-- Received a customer feedback: [" + req.body.feedback + "]");

res.send("<html><head><title>WTCU Feedback</title><script>setTimeout(function(){window.location.href='/'},3000);</script></head><body>Thanks for your feedback!</body></html>");

};

self.routes['/'] = function(req, res) {

res.setHeader('Content-Type', 'text/html');

res.send(self.cache_get('index.html') );

};

};

/**

* Initialize the server (express) and create the routes and register

* the handlers.

*/

self.initializeServer = function() {

self.createRoutes();

//self.app = express.createServer();

self.app = express();

self.app.set('port', process.env.PORT || 3333);

self.app.set('ip', process.env.IP || "127.0.0.1");

self.app.use(express.static(__dirname));

//self.app.use(express.bodyParser());

self.app.use(express.json());

self.app.use(express.urlencoded());

// Add handlers for the app (from the routes).

for (var r in self.routes) {

self.app.get(r, self.routes[r]); // maps the HTTP GET request

self.app.post(r, self.routes[r]); // maps the HTTP POST request

}

};

/**

* Initializes the sample application.

*/

self.initialize = function() {

self.setupVariables();

self.populateCache();

self.setupTerminationHandlers();

// Create the express server and routes.

self.initializeServer();

};

/**

* Start the server (starts up the sample application).

*/

self.start = function() {

// Start the app on the specific interface (and port).

self.app.listen(self.app.get('port'), function() {

console.log('%s: Node server started on %s:%d ...',

Date(Date.now() ), self.app.get('ip'), self.app.get('port'));

});

};

}; /* Sample Application. */

/**

* main(): Main code.

*/

var zapp = new SampleApp();

zapp.initialize();

zapp.start();

feedback.js

<?xml version="1.0" encoding="iso-8859-1"?>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml">

<head>

<title>Wake Tech Credit Union</title>

<link rel="stylesheet" type="text/css" href="css/interface.css" />

<style>

* {

font-family: Verdana, Arial, sans-serif;

}

a:link {

color:#000;

text-decoration: none;

}

a:visited {

color:#000;

}

a:hover {

color:#33F;

}

.button {

background: -webkit-linear-gradient(top,#008dfd 0,#0370ea 100%);

border: 1px solid #076bd2;

border-radius: 3px;

color: #fff;

display: none;

font-size: 13px;

font-weight: bold;

line-height: 1.3;

padding: 8px 25px;

text-align: center;

text-shadow: 1px 1px 1px #076bd2;

letter-spacing: normal;

}

.center {

padding: 10px;

text-align: center;

}

.final {

color: black;

padding-right: 3px;

}

.interim {

color: gray;

}

.info {

font-size: 14px;

text-align: center;

color: #777;

display: none;

}

.right {

float: right;

}

.sidebyside {

display: inline-block;

width: 45%;

min-height: 40px;

text-align: left;

vertical-align: top;

}

#headline {

font-size: 40px;

font-weight: 300;

}

#info {

font-size: 20px;

text-align: center;

color: #777;

visibility: hidden;

}

#results {

font-size: 14px;

font-weight: bold;

border: 1px solid #ddd;

padding: 15px;

text-align: left;

min-height: 150px;

}

#start_button {

border: 0;

background-color:transparent;

padding: 0;

}

</style>

</head>

<body>

<div id="page">

<a id="top"><img src="images/logo.jpg" alt="Wake Tech Credit Union" />

<div id="navigation">

<a href="index.html">HOME</a>

<a href="tools.html">TOOLS</a>

<a href="highlights.html">HIGHLIGHTS</a>

<a href="hours.html">HOURS</a>

<a href="contact.html">CONTACT</a>

<a>FEEDBACK</a>

</div>

<h1>Feedback</h1>

<div id="info">

<p id="info_start">We would like to hear from you. Click on the microphone icon and begin speaking.</p>

<p id="info_speak_now">Speak now.</p>

<p id="info_no_speech">No speech was detected. You may need to adjust your

<a href="//support.google.com/chrome/bin/answer.py?hl=en&amp;amp;answer=1407892">

microphone settings</a>.</p>

<p id="info_no_microphone">

No microphone was found. Ensure that a microphone is installed and that

<a href="//support.google.com/chrome/bin/answer.py?hl=en&amp;amp;answer=1407892">

microphone settings</a> are configured correctly.</p>

<p id="info_allow">Click the "Allow" button above to enable your microphone.</p>

<p id="info_denied">Permission to use microphone was denied.</p>

<p id="info_blocked">Permission to use microphone is blocked. To change,

go to chrome://settings/contentExceptions#media-stream</p>

<p id="info_upgrade">Web Speech API is not supported by this browser.

Upgrade to <a href="//www.google.com/chrome">Chrome</a>

version 25 or later.</p>

</div>

<div class="right">

<button id="start_button">

<img id="start_img" src="images/mic.gif" alt="Start"></button>

</div>

<div id="results">

<span id="final_span" class="final"></span>

<span id="interim_span" class="interim"></span>

<p>

</div>

<div class="center">

<button id="send_button" class="button">

Send Feedback</button>

<div id="send_info" class="info">

We appreciate your feedback.

</div>

<p>

<div id="div_language">

<select id="select_language"></select>

&nbsp;&nbsp;

<select id="select_dialect"></select>

</div>

</div>

<script>

var langs =

[['Afrikaans', ['af-ZA']],

['Bahasa Indonesia',['id-ID']],

['Bahasa Melayu', ['ms-MY']],

['Català', ['ca-ES']],

['eština', ['cs-CZ']],

['Deutsch', ['de-DE']],

['English', ['en-AU', 'Australia'],

['en-CA', 'Canada'],

['en-IN', 'India'],

['en-NZ', 'New Zealand'],

['en-ZA', 'South Africa'],

['en-GB', 'United Kingdom'],

['en-US', 'United States']],

['Español', ['es-AR', 'Argentina'],

['es-BO', 'Bolivia'],

['es-CL', 'Chile'],

['es-CO', 'Colombia'],

['es-CR', 'Costa Rica'],

['es-EC', 'Ecuador'],

['es-SV', 'El Salvador'],

['es-ES', 'España'],

['es-US', 'Estados Unidos'],

['es-GT', 'Guatemala'],

['es-HN', 'Honduras'],

['es-MX', 'México'],

['es-NI', 'Nicaragua'],

['es-PA', 'Panamá'],

['es-PY', 'Paraguay'],

['es-PE', 'Perú'],

['es-PR', 'Puerto Rico'],

['es-DO', 'República Dominicana'],

['es-UY', 'Uruguay'],

['es-VE', 'Venezuela']],

['Euskara', ['eu-ES']],

['Français', ['fr-FR']],

['Galego', ['gl-ES']],

['Hrvatski', ['hr_HR']],

['IsiZulu', ['zu-ZA']],

['Íslenska', ['is-IS']],

['Italiano', ['it-IT', 'Italia'],

['it-CH', 'Svizzera']],

['Magyar', ['hu-HU']],

['Nederlands', ['nl-NL']],

['Norsk bokmål', ['nb-NO']],

['Polski', ['pl-PL']],

['Português', ['pt-BR', 'Brasil'],

['pt-PT', 'Portugal']],

['Român', ['ro-RO']],

['Slovenina', ['sk-SK']],

['Suomi', ['fi-FI']],

['Svenska', ['sv-SE']],

['Türkçe', ['tr-TR']],

['', ['bg-BG']],

['P', ['ru-RU']],

['', ['sr-RS']],

['', ['ko-KR']],

['', ['cmn-Hans-CN', ' ()'],

['cmn-Hans-HK', ' ()'],

['cmn-Hant-TW', ' ()'],

['yue-Hant-HK', ' ()']],

['', ['ja-JP']],

['Lingua latna', ['la']]];

for (var i = 0; i < langs.length; i++) {

select_language.options[i] = new Option(langs[i][0], i);

}

select_language.selectedIndex = 6;

updateCountry();

select_dialect.selectedIndex = 6;

showInfo('info_start');

function updateCountry() {

for (var i = select_dialect.options.length - 1; i >= 0; i--) {

select_dialect.remove(i);

}

var list = langs[select_language.selectedIndex];

for (var i = 1; i < list.length; i++) {

select_dialect.options.add(new Option(list[i][1], list[i][0]));

}

select_dialect.style.visibility = list[1].length == 1 ? 'hidden' : 'visible';

}

var send_feedback = false;

var final_transcript = '';

var recognizing = false;

var ignore_onend;

var start_timestamp;

if (!('webkitSpeechRecognition' in window)) {

upgrade();

} else {

start_button.style.display = 'inline-block';

var recognition = new webkitSpeechRecognition();

recognition.continuous = true;

recognition.interimResults = true;

recognition.onstart = function() {

recognizing = true;

showInfo('info_speak_now');

start_img.src = 'images/mic-animate.gif';

};

recognition.onerror = function(event) {

if (event.error == 'no-speech') {

start_img.src = 'images/mic.gif';

showInfo('info_no_speech');

ignore_onend = true;

}

if (event.error == 'audio-capture') {

start_img.src = 'images/mic.gif';

showInfo('info_no_microphone');

ignore_onend = true;

}

if (event.error == 'not-allowed') {

if (event.timeStamp - start_timestamp < 100) {

showInfo('info_blocked');

} else {

showInfo('info_denied');

}

ignore_onend = true;

}

};

recognition.onend = function() {

recognizing = false;

if (ignore_onend) {

return;

}

start_img.src = 'images/mic.gif';

if (!final_transcript) {

showInfo('info_start');

return;

}

showInfo('');

if (window.getSelection) {

window.getSelection().removeAllRanges();

var range = document.createRange();

range.selectNode(document.getElementById('final_span'));

window.getSelection().addRange(range);

}

if (send_feedback) {

send_feedback = false;

sendFeedback();

}

};

recognition.onresult = function(event) {

var interim_transcript = '';

for (var i = event.resultIndex; i < event.results.length; ++i) {

if (event.results[i].isFinal) {

final_transcript += event.results[i][0].transcript;

} else {

interim_transcript += event.results[i][0].transcript;

}

}

final_transcript = capitalize(final_transcript);

final_span.innerHTML = linebreak(final_transcript);

interim_span.innerHTML = linebreak(interim_transcript);

if (final_transcript || interim_transcript) {

showButtons('inline-block');

}

};

}

function upgrade() {

start_button.style.visibility = 'hidden';

showInfo('info_upgrade');

}

var two_line = / /g;

var /g;

function linebreak(s) {

return s.replace(two_line, '<p></p>').replace(one_line, '<br>');

}

var first_char = /S/;

function capitalize(s) {

return s.replace(first_char, function(m) { return m.toUpperCase(); });

}

function sendFeedback() {

/*

var n = final_transcript.indexOf(' ');

if (n < 0 || n >= 80) {

n = 40 + final_transcript.substring(40).indexOf(' ');

}

var subject = encodeURI(final_transcript.substring(0, n));

var body = encodeURI(final_transcript.substring(n + 1));

window.location.href = 'mailto:?subject=' + subject + '&body=' + body;

*/

//alert("Your feedback has been sent. Thank you!");

var feedbackform = document.createElement("FORM");

feedbackform.name="feedbackform";

feedbackform.method = "POST";

feedbackform.action = "/feedback";

var forminput = document.createElement("INPUT");

forminput.type = "TEXT";

forminput.name = "feedback";

forminput.value = final_transcript;

feedbackform.appendChild(forminput);

document.body.appendChild(feedbackform); // added for newer browsers

feedbackform.submit();

}

function sendButton() {

if (recognizing) {

send_feedback = true;

recognizing = false;

recognition.stop();

} else {

sendFeedback();

}

send_button.style.display = 'none';

send_info.style.display = 'inline-block';

showInfo('');

}

function startButton(event) {

if (recognizing) {

recognition.stop();

return;

}

final_transcript = '';

recognition.lang = select_dialect.value;

recognition.start();

ignore_onend = false;

final_span.innerHTML = '';

interim_span.innerHTML = '';

start_img.src = 'images/mic-slash.gif';

showInfo('info_allow');

showButtons('none');

start_timestamp = event.timeStamp;

}

function showInfo(s) {

if (s) {

for (var child = info.firstChild; child; child = child.nextSibling) {

if (child.style) {

child.style.display = child.id == s ? 'inline' : 'none';

}

}

info.style.visibility = 'visible';

} else {

info.style.visibility = 'hidden';

}

}

var current_style;

function showButtons(style) {

if (style == current_style) {

return;

}

current_style = style;

//copy_button.style.display = style;

send_button.style.display = style;

//copy_info.style.display = 'none';

send_info.style.display = 'none';

}

</script>

  

</div>

</body>

</html>

You need to submit only the modified app.js file..

I already downloaded the moment model.

Explanation / Answer

Node.js makes it possible to write applications in JavaScript on the server.It's built on the V8 JavaScript runtime and written in C++ - so it's fast.Originally, it was intended as a server environment for applications, but developers started using it to create tools to aid them in local task automation. Since then, a whole new ecosystem of Node-based tools ( such as Grunt, Gulp and Webpack ) has envolved to transform the face of front-end development.

To make use of these tools ( or packages) in Node.js we need to be able to install and manage them in a useful way. This is where npm, the Node package manager, comes in. It installs the packages you want to use and provides a useful interface to work with them.

You might consider installing Node using a version manager. This negates the permission issue raised in the next section.

let's see where node was installed and check the version.

$ which node /usr/bin/node $ node -- version v6.10.3

To verify that your installation was successful let's give Node's REPL a try.

$ node >console.log("Node is running'); Node is running > .help .break Sometimes you get stuck, this gets you out .clear Alias for .break .exit Exit the repl .help Show repl options .load Load JS from a file into the REPL session .save Save all evaluated commands in this REPL session to a file > .exit

The Node.js installation worked, so we can now focus our attention on npm, which was included in the install.

$ which npm /usr/bin/npm $ npm -- version 3.10.10

Node Packaged Modules

npm can install packages in local or global mode. In local mode it installs the package in a node_modules folder in your parent working directory. This location is owned by the current user. Global packages are installed in {prefix}/lib/node_modules/ which is owned by root ( where {prefix} is usually /usr/ or /usr/local). This means you would have to use sudo to install packages globally, which could cause permission errors when resolving third-party dependencies, as well as being a security concern. Lets change that:

Changing the Location of Global Packages

Let's see what output npm config gives us.

$ npm config list ; cli configs user-agent = "npm/3.10.10 node/v6.10.3 linux x64"

;userconfig /home/sitepoint/.npmrc prefix = "/home/sitepoint/.node_modules_global"

; node bin location = /usr/bin/nodejs ; cwd = /home/sitepoint ; HOME = /home/sitepoint ; "npm config is -I" to show all defaults.

Installing Packages in Global Mode

At the moment we only have one package installed globally - that is the npm package itself. So let's change that and install UglifyJs (a JavaScript minification tool). We use the --global flag, but this can be abbreviated to -g.

$ npm install uglify-js --global /home/sitepoint/.node_modules_global/ bin/uglifyjs -> /home/sitepoint/ .node_modules_global/lib/ node_modules/uglify-js/bin/uglifyjs + uglify-js@3.0.15 added 4 packages in 5.836s

  

Hire Me For All Your Tutoring Needs
Integrity-first tutoring: clear explanations, guidance, and feedback.
Drop an Email at drjack9650@gmail.com
Chat Now And Get Quote