2

I am playing around and trying to learn the MEAN stack to create a single page application. I was able to get my back-end routes to work correctly. I've tested it using Postman and get the results I expect, however I cannot get my front-end to talk to the back-end correctly.

I reduced my front-end to very basic html and javascript, but still get a syntax error "Unexpected token <". When I inspect my coreTest.js file in the browser, I see that it's just a copy of my html file, rather than javascript code.

When I run index.html by itself (without server.js) coreTest.js runs just fine. I'm not sure why, when running my server.js file, my coreTest.js file doesn't work properly.

server.js

// Setup

var express = require('express');
var app = express();            // create app w/ express

var mongoose = require('mongoose');             // used for MongoDB connection
var morgan = require('morgan');             // log requests to the console
var bodyParser = require('body-parser');            // pull information from HTML POST
var methodOverride = require('method-override');            // simulate DELETE and PUT requests


// Configure

mongoose.connect('localhost:27017/test');       // connect to localhost db "test"

// varify connection
var db = mongoose.connection;
db.on('error', console.error.bind(console, 'connection error: '));

app.use(express.static(__dirname + '/public'));         // set static files location
app.use(morgan('dev'));         // log every request to console
app.use(bodyParser.urlencoded({'extended':'true'}));        // parse application/x-www-form-url
app.use(bodyParser.json());
app.use(bodyParser.json({ type: 'application/vnd.api+json' })); // parse vnd.api+json as json
app.use(methodOverride());

// define db model
var Todo = mongoose.model('Todo', {
    text: String
});


var router = express.Router();

router.route("/todos")

    .get(function(req, res) {
        Todo.find(function(err, todos) {
            if (err)
                res.send(err);

            res.json(todos);
        });
    })

    .post(function(req, res) {
        var todo = new Todo();
        todo.text = req.body.text;

        todo.save(function(err) {
            if (err)
                res.send(err);

            res.json({mes: "Todo item created"});
        })
    });

router.route("/todos/:todo_id")

    .delete(function(req, res) {
        Todo.remove( {
            _id: req.params.todo_id
        }, function(err, todo) {
            if (err)
                res.send(err);

            res.json({mes: "Successfully deleted"});
        });
    });

// route to application
router.route("*")
    .get(function(req, res) {
        res.sendfile('./public/index.html');
    });

// Register our routes
app.use('/api', router);

// Listen, start node app
app.listen(8080);
console.log("app listening on port 8080");

coreTest.js

alert("ping");

index.html

<!doctype html>
<html lang="en">
<head>
    <meta charset="UTF-8">

    <title>Starter MEAN Single Page Application</title>
    <script type="text/javascript" src="coreTest.js"></script>

</head>
<body>

    I did it!! Wooo!!

</body>
</html>
sainid
  • 82
  • 6

2 Answers2

0

I suspect the problem is between

app.use(express.static(__dirname + '/public'));   

and

// route to application
router.route("*")
.get(function(req, res) {
    res.sendfile('./public/index.html');
});

When you're running the server, your client-side code is trying to load "coreTest.js", which is matched by the last rule ; and so the server returns the content of index.html.

I'm not sure what you mean about "runing index.html by itself" ; if you mean "visiting file://..../public/index.html", it works because the browser will try to load coreTest.js from your file system.

Try using the "static" plugin only to serve files from "public", and use this prefix in the client side code :

app.use("/public", express.static(...))

and in the client

<script type=".." src="public/coreTest.js"></script>

Getting the path rights will depend on what's on your disk.

This might help, too : static files with express.js

Community
  • 1
  • 1
phtrivier
  • 13,047
  • 6
  • 48
  • 79
0

I was able to solve my issue using what phtrivier recommended.

Instead of serving my files from "public" I chose to serve them from "api" because I already set my router to take requests from that path as well.

app.use("/api", express.static(__dirname + '/public'));

I didn't need to change my reference to coreTest.js in the html because my files were organized with coreTest already in the root directory like this:

public
   -index.html
   -coreTest.js
sainid
  • 82
  • 6