I'm trying to develop node.js app with express.js. One of the thing which I try to implement is a function to serve generated by browserify bundle js file. What I would like to do is to use maven-download-plugin to download that file and put into my repository (it's java app). I know that his is a bit complicated but that's how it's look like. I can generate bundle with browserify using code:
browserify("./path/myjs.js", {
gzip : true
});
b.transform("hbsfy");
b = b.bundle({standalone: 'bundle'});
However I cannot find any information how to write that information to the public/bundle.js and how to serve it when for example path /bundle.js will be requested.
Any ideas how can I do that?
Well, why don't you just use static module for express?
var express = require('express');
var app = express();
app.use(express.static(__dirname + '/public'));
To write bundle to the file, just stream it...
var fs = require('fs');
var ws = fs.createWriteStream(__dirname + '/public/bundle.js');
b.bundle({standalone: 'bundle'}).pipe(ws);
Or you can do it completely on-fly avoiding file-system and streaming directly to client...
app.get('/bundle.js', function(req, res, next) {
b.bundle({standalone: 'bundle'}).pipe(res);
});
Related
I am currently trying integrate the Mixpanel Node library into a test application that I am building. This is a Node.js application using the express framework.
As per the express docs, I have a JS file to manage the project, a folder called "public" that contains all of my static files, and another folder with the node modules that come with express.
I have two static HTML pages in "public" that I am trying to put mixpanel tracking into. I am running the project locally by running node app.js.
app.js includes:
const express = require('express');
const app = express();
const port = 3000;
const path = require('path');
//Mixpanel Additions
var Mixpanel = require('mixpanel');
var mixpanel = Mixpanel.init('<I am putting my project token here>', {
protocol: 'https'
});
//App Configuration and Init
app.use(express.static('public'));
app.get('/', (req, res) => {
res.sendFile(path.join(__dirname + '/public/page.html'));
});
app.listen(port, () => console.log(`Example app listening on port ${port}!`))
In my HTML files I try to use mixpanel functions by putting them into script tags:
<script>
mixpanel.track("event")
</script>
But when I run node app.js and view the page in my browser it says:
Uncaught ReferenceError: mixpanel is not defined
I have a pretty poor understanding of node.js, but I am imagining that I need to use app.use(), app.get(), or something along those lines to get the Mixpanel lib loaded into the app. What am I doing wrong? I also realize that my understanding of Express and Node is pretty rudimentary, so any additional knowledge is appreciated, especially if I am way off.
If you want to call mixpanel tracking functions in the browser, you should load the mixpanel library in a script tag on the browser side, as seen here:
https://developer.mixpanel.com/docs/javascript
The purpose of the node.js package is to send events from the server side, like if you wanted to log when page.html is rendered, you could do
app.get('/', (req, res) => {
res.sendFile(path.join(__dirname + '/public/page.html'));
mixpanel.track('event')
});
I'm fairly new at web development and I've been having an issue with requiring certain node modules in my Express application. I need to access certain code, but I'm having difficulty with the the intricacies of Node, and can't for the life of me access node_modules where I need to.
What I'm attempting to do is utilize the Cloudinary video-player from the node_modules that I've installed. I've included path links in the index.html file which is served from htmlRoutes.js, and I've explicitly directed express to statically load these files within the document, but the application does not recognize these paths as valid. I've tried requiring these modules in separate JS files served up from the public folder, but that's also invalid. From what I understand it might be my own confusion of client-side vs server-side programming, but I don't know how to resolve this, nor what resources I should be reading in order to do so.
Any help would be appreciated. Here's what my server looks like:
const express = require("express");
const path = require('path');
const bodyParser = require('body-parser');
const baguetteBox = require('baguettebox.js');
const cloudinary = require('cloudinary');
const axios = require("axios");
const app = express();
// Define a port to listen for incoming requests
// Sets an initial port. We"ll use this later in our listener
const PORT = process.env.PORT || 8181;
app.use(express.static('public'));
//static routes that attempts to fetch scripts from node_modules without revealing inner directory structure
app.use(express.static(__dirname + '/node_modules/lodash'));
app.use(express.static(__dirname + '/node_modules/cloudinary'));
app.use(express.static(__dirname + '/node_modules/cloudinary-core'));
app.use(express.static(__dirname + '/node_modules/cloudinary-video-player'));
// Sets up the Express app to handle data parsing
app.use(bodyParser.urlencoded({ extended: false }));
app.use(bodyParser.json());
//routes
require("./routes/htmlRoutes.js")(app);
// require("./routes/apiRoutes.js")(app);
//configure cloudinary api calls
// cloudinary.config({
// cloud_name: 'name',
// api_key: 'key',
// api_secret: 'secret',
// secure: true
// })
// Start our server so that it can begin listening to client requests.
app.listen(PORT, function() {
// Log (server-side) when our server has started
console.log("App listening on: http://localhost:" + PORT);
});
I have never seen node_modules packages served as static files directly, having said that, I will be agnostic with that working.
An alternative way to deal with this issue is to use a bundler such as Webpack and serve it with Express.js
The reason for this is that even being JavaScript, Webpack will compile the code into something interpretable by the browser, something that in many cases you do not find in a package of Node.js
If you need for example lodash, you dont have to access to node_modules/lodash. Just import lodash by declaring:
const lodash = require('lodash');
And you can now use lodash in the file you declaring lodash.
I use express to serve angular html file. I want to test if angular can get data from express backend.
app.component.html
<h1>
{{title}}
</h1>
<a class="button" href="/Books/getall">Get all books</a>
server.js
const express = require('express');
var app = express();
var staticRoot = __dirname;
app.set('port', (process.env.PORT || 3000));
var bookRouter = require('./bookController');
app.use(express.static(staticRoot));
app.get('/', function(req, res) {
res.sendFile('index.html');
});
app.use('/Books', bookRouter);
app.listen(app.get('port'), function() {
console.log('app running on port', app.get('port'));
});
bookController.js
var express = require('express');
var mongoose = require('mongoose');
var Books = require('./books.model');
var bookRouter = express.Router();
var router = function(){
bookRouter.use('/getall')
.get(function(req, res){
var url = 'mongodb://admin:password#ds019076.mlab.com:19076/booksdbtest';
mongoose.connect(url, function(err){
Books.find()
.exec(function(err, results){
res.send(results);
mongoose.disconnect();
});
});
});
};
module.exports = router;
But I got some error like I mentioned on the title. I have read some articles and discussions that says i need some proxy when using express and angular 2 together but I really don't know how to implement that. Can someone help me here on what is wrong with the code? That would be so much appreciated.
EDIT:
I have found what caused the error. I have changed bookRouter.use -> bookRouter.route and the error is gone. Now another problem appears. If I click the link it will load continously and nothing happens. Anyone know why?
If you are using Angular2 with Express you need to hand off the front end routes to Angular2 and then use Express for the back end points.
In most cases you will receive problems not using some sort of template engine. I like to use Express-Handlebars.
npm install hbs
Once you have this installed you can set it up in your app.js file. The file you set Express up in.
// view engine setup
app.set('views', path.join(__dirname, 'public'));
app.set('view engine', 'hbs');
Also make sure you have a public directory. If not create one.
/public
Then in the app.js
app.use(express.static(path.join(__dirname, '/public')));
Now you can put css, js, or images in this directory and call them inside your app.
Also inside the public directory you can put your index.hbs file.
Express-Handlebars uses hbs files. In our case you are only going to need one.
This is the file you would need to put the head of your html file in. As well as the
<my-app>Loading...</my-app>
We will pass this off to Angular2.
Now that we have that setup lets make a route to pass it off.
/routes/index.js
var express = require('express');
var router = express.Router();
// pass front end off to Angular2
router.get('/', function(req, res, next) {
res.render('index');
});
module.exports = router;
So now when the app loads it will load that index page. So that is the only route we need for now to pass the front end off. At this point we will configure angular2.
Webpack
What is Webpack?
Webpack is a powerful module bundler. A bundle is a JavaScript file
that incorporate assets that belong together and should be served to
the client in a response to a single file request. A bundle can
include JavaScript, CSS styles, HTML, and almost any other kind of
file.
I do not know how you have included Angular2 into your project. But if you have not set it up yet and do not know how I suggest using Webpack
Follow this tutorial to get it setup. Sometimes it is easier to start over.
Angular2
If you go into your Angular2 application now which for me is at
/assets/app/
You will set up your components and their own routing. Any links created for the front views will be done here now. So in the /assets/app directory you will need a app.routing.ts file.
Routing in Angular2
There are many ways to build this file. I like to use templates then child templates which would be to much to explain in this answer. For you though a basic routing file will look like this.
import { Routes, RouterModule } from "#angular/router";
import { AboutComponent } from './about.component';
import { HomeComponent } from './home.component';
const APP_ROUTES: Routes = [
{ path: '', redirectTo: 'home', pathMatch: 'full' },
{ path: 'home', component: HomeComponent },
{ path: 'about', component: AboutComponent },
];
export const routing = RouterModule.forRoot(APP_ROUTES);
Links
Now that you have routes setup in Angular2 you can create links in your html files or home.component.html like this,
<li class="nav-item p-x-1">
<a class="nav-link" routerLinkActive="active" [routerLink]="['/home']"> Home</a>
</li>
I realize this has not basically given you code that will compile which in a perfect world we would all share like that. But I really understand the struggle and want to help. There is just to much to explain to be able to hand you over that much and it make sense. Please use the tutorial I gave you above. If you have any questions ask. Try and use my answer as a baseline to understand the different components of putting together an application like this.
Disclaimer
You do not have to use Express-Handlebars. If you find in that tutorial they are doing something different just follow along so you can get a working app you understand. I like hbs because I only use it for one file then handle everything on the front end with Angular2. The reason I use it instead of just an html file is because it is a huge pain to configure Express to work right with Angular2. For example if you just use an html file then add it to the public directory then run your app and refresh the page you will get a 404 error. Unless you add something like,
HashLocationStrategy
Which adds ugly hash tags to your url and is annoying in a whole different way. Using a template engine for that small task makes everything work so much easier and better. The configuration is minimal as you can see above.
For a seed project I use,
git clone https://github.com/wuno/md-recruit.git
in the terminal navigate to the new directory you just cloned.
type,
webpack
Then
npm start
Then navigate to localhost:3000
Make sure you have webpack installed globally
npm install webpack -g
It is very important that what ever version of webpack is installed locally in your project has to match the global install.
i am using one npm package for generating QR code after it will save the image in qr directory and after i cant access the file with my app and also directly. i think it is the problem of middleware.(i can acces the images after sails restating, it is working on my localhost). each time a user using my app it will automatically generate qr for the user changes.
You have plenty of ways to do that.
Create a symlink in asset (eg: assets/app) pointing to your qrcode folder
You can access express trough sails.express. So you can add in your config/bootstrap :
var express = require('express');
sails.express.app.use(express.static(process.cwd() + '/qrcode_folder'));
Custom middleware. Add in your config/http.js :
var express = require('express');
module.exports.express = {
qrCodeMiddleware: function (app) {
app.use(express.compress());
app.use('/qrcode', express.static(process.cwd() + '/my_qrcode_folder'));
}
};
I'm trying to build a simple searching/browsing service for a server and I thought it could be interesting to use express for that to get familiar with it.
For the problem I'm considering, I have express#3.4.1 and a very simple app.js
var express = require("express");
var app = express();
//var express = require('express')
//, app = express.createServer();
app.configure(function() {
var hourMs = 1000*60*60;
app.use(express.static(__dirname + '/public', { maxAge: hourMs }));
app.use(express.directory(__dirname + '/public', {hidden: true, icons: true}));
app.use(express.errorHandler());
});
app.listen(1333);
How can I style/customize the HTML/CSS that the directory middleware produces ?
Should I overwrite express.directory.html in my app.js or is there a better/cleaner way ?
Edit : after looking at the code it seems overriding the function is not the way to go. the file it uses seems rather hard coded and I may end up copying the whole file to override what I want. So, any idea ?
You could extract all relevant code from the Express middleware, make your own adjustments, and save it as part of your app (as ./lib/middleware/directory.js or something).
If you're going to modify the files inside the node_modules/ directory you can be sure that you'll lose any modifications when you update.
You could rewrite express.directory.html(), but you might still run into the problem that any updates make it stop working because of internal changes.
I believe directly editing the node_modules/express/node_modules/connect/lib/public/style.css and directory.html would be the cleanest way of customizing the default express directory style/html.