skip to Main Content

I am uploading my node.js code on Azure web app. After a lot of try, I was able to successfully do it. I am building my code on Visual Studio and pushing to Github and using CI/CD connected to Azure web app. Recently, I connected my code to Azure MySQL server and after that, I have started getting error. I found in the logs that port 8080 is not working. Here’s a snippet of the error:

[DATE] ERROR - Container [CONTAINER_ID] for site [SITE_NAME] has exited, failing site start

[DATE] ERROR - Container [CONTAINER_ID] didn't respond to HTTP pings on port: 8080, failing site start. See container logs for debugging.

[DATE] INFO  - Stopping site [SITE_NAME] because it failed during startup.

[DATE] Error details:

  code: 'MODULE_NOT_FOUND',

  requireStack: [ '/home/site/wwwroot/node_modules/express/lib/router/index.js', '/home/site/wwwroot/node_modules/express/lib/application.js', '/home/site/wwwroot/node_modules/express/lib/express.js', '/home/site/wwwroot/node_modules/express/index.js', '/home/site/wwwroot/server.js'

  ]

[DATE] INFO  - Starting container for site

[DATE] INFO  - docker run -d --expose=8080 --name [CONTAINER_NAME] [ENVIRONMENT_VARIABLES] appsvc/node:20-lts_[VERSION] node server.js

[DATE] INFO  - Initiating warmup request to container [CONTAINER_ID] for site [SITE_NAME]

[DATE] ERROR - Container [CONTAINER_ID] for site [SITE_NAME] has exited, failing site start

[DATE] ERROR - Container [CONTAINER_ID] didn't respond to HTTP pings on port: 8080, failing site start. See container logs for debugging.

[DATE] INFO  - Stopping site [SITE_NAME] because it failed during startup.

I am not using Docker. I am various measures to do it. Here’s a screenshot of my Web app config. I have added port as 8080:
enter image description here

Here’s my Github workflow:

name: Build and deploy Node.js app to Azure Web App

on:

  push:

    branches:

      - main

  workflow_dispatch:

jobs:

  build-and-deploy:

    runs-on: ubuntu-latest

    steps:

    - uses: actions/checkout@v2

    - name: Set up Node.js version

      uses: actions/setup-node@v1

      with:

        node-version: '20.15.1'

    - name: Create .npmrc file

      run: echo "engine-strict=false" > .npmrc

    - name: Install server dependencies

      run: npm ci

    - name: Build client

      run: |

        cd client

        npm ci

        npm run build

        cd ..

    - name: Create deployment package

      run: |

        zip -r deploy.zip . -x "*.git*" "node_modules/*" "client/node_modules/*" "client/src/*" "client/public/*"

    - name: 'Deploy to Azure Web App'

      uses: azure/webapps-deploy@v2

      with:

        app-name: 'job-search'

        publish-profile: ${{ secrets.AZURE_WEBAPP_PUBLISH_PROFILE }}

        package: ./deploy.zip

    - name: Print server.js content

      run: |

        echo "Contents of server.js:"

        cat server.js

    - name: Print Node.js version

      run: node --version

Here’s my server.js:

console.log('Starting server.js');

console.log('Environment variables:', {

  NODE_ENV: process.env.NODE_ENV,

  PORT: process.env.PORT,

  DB_HOST: process.env.DB_HOST,

  DB_USER: process.env.DB_USER,

  DB_NAME: process.env.DB_NAME

  // Don't log DB_PASSWORD

});

process.on('uncaughtException', (err) => {

  console.error('Uncaught Exception:', err);

});

const express = require('express');

const cors = require('cors');

const cron = require('node-cron');

const path = require('path');

const { initializeDatabase } = require(path.join(__dirname, 'server', 'database'));

const { fetchAllJobs, searchJobs, getJobCategories, getCategoryCount, getTotalJobCount } = require(path.path.join(__dirname, 'server', 'jobLogic'));

const app = express();

const port = process.env.PORT || 8080;

// Middleware

app.use(cors());

app.use(express.json());

// Serve static files from the React app

app.use(express.static(path.join(__dirname, 'client/build')));

app.get('/health', (req, res) => {

  res.status(200).send('OK');

});

app.get('*', (req, res) => {

  res.sendFile(path.join(__dirname, 'client/build', 'index.html'));

});

// Error handling middleware

app.use((err, req, res, next) => {

  console.error(err.stack);

  res.status(500).send('Something broke!');

});

app.use((req, res, next) => {

  res.status(404).send("404 - Not Found");

});

// Initialize database and start server

initializeDatabase()

  .then(() => {

    console.log('Database initialized successfully');

    return new Promise((resolve) => {

      const server = app.listen(port, () => {

        console.log(`Server running at http://localhost:${port}`);

        resolve(server);

      });

    });

  })

  .then((server) => {

    console.log('Server started successfully');

    return fetchAllJobs();

  })

  .then(() => {

    console.log('Initial job fetch completed');

  })

  .catch(error => {

    console.error('Error during startup:', error);

    process.exit(1);

  });

// Schedule job fetching (every 6 hours)

//cron.schedule('0 */6 * * *', fetchAllJobs);

This is package.json for server level:

{
  "name": "job-search",
  "version": "0.1.0",
  "main": "server.js",
  "private": true,
  "dependencies": {
    "@testing-library/jest-dom": "^5.17.0",
    "@testing-library/react": "^13.4.0",
    "@testing-library/user-event": "^13.5.0",
    "axios": "^1.7.2",
    "cheerio": "^1.0.0-rc.12",
    "cors": "^2.8.5",
    "csv-parser": "^3.0.0",
    "express": "^4.19.2",
    "lottie-react": "^2.4.0",
    "mysql2": "^3.10.3",
    "node-cache": "^5.1.2",
    "node-cron": "^3.0.3",
    "react": "^18.3.1",
    "react-dom": "^18.3.1",
    "react-scripts": "5.0.1",
    "source-map-support": "^0.5.21",
    "sqlite": "^5.1.1",
    "sqlite3": "^5.1.7",
    "us-state-codes": "^1.1.2",
    "web-vitals": "^2.1.4"
  },
  "scripts": {
    "start": "node server.js",
    "build": "cd client && npm install && npm run build",
    "test": "react-scripts test",
    "eject": "react-scripts eject",
    "dev": "react-scripts start",
    "postinstall": "npm run build"
  },
  "eslintConfig": {
    "extends": [
      "react-app",
      "react-app/jest"
    ]
  },
  "browserslist": {
    "production": [
      ">0.2%",
      "not dead",
      "not op_mini all"
    ],
    "development": [
      "last 1 chrome version",
      "last 1 firefox version",
      "last 1 safari version"
    ]
  },
  "engines": {
    "node": "20.15.1"
  },
  "devDependencies": {
    "@babel/core": "^7.24.9",
    "@babel/preset-env": "^7.24.8",
    "babel-loader": "^9.1.3",
    "nodemon-webpack-plugin": "^4.8.2",
    "start-server-webpack-plugin": "^2.2.5",
    "webpack": "^5.93.0",
    "webpack-cli": "^5.1.4",
    "webpack-node-externals": "^3.0.0"
  }
}

I am trying various steps to solve it. But it seems my main issue is with port 8080. Any help with be appreciated.

2

Answers


  1. The error you are facing is not about Http pings, It is related to Module_Not_Found. Which means the files are not deployed to Azure correctly.

    code: ‘MODULE_NOT_FOUND’,

    requireStack: [
    ‘/home/site/wwwroot/node_modules/express/lib/router/index.js’,
    ‘/home/site/wwwroot/node_modules/express/lib/application.js’,
    ‘/home/site/wwwroot/node_modules/express/lib/express.js’,
    ‘/home/site/wwwroot/node_modules/express/index.js’,
    ‘/home/site/wwwroot/server.js’

    ]

    Check Kudu to see if the files are deployed correctly.

    • Open below URL to see the files.
      https://<YourAzurewebappName>.scm.azurewebsites.net/newui

    • Open FileManager => Site => wwwroot, here you can find your deployed files.

    enter image description here

    Project Structure:

    enter image description here

    Below is my code.

    server.js:

    require('dotenv').config();
    console.log('Starting server.js');
    console.log('Environment variables:', {
      NODE_ENV: process.env.NODE_ENV ,
      PORT: process.env.PORT,
      DB_HOST: process.env.DB_HOST,
      DB_USER: process.env.DB_USER,
      DB_PASSWORD:process.env.DB_PASSWORD,
      DB_NAME: process.env.DB_NAME
    });
    process.on('uncaughtException', (err) => {
      console.error('Uncaught Exception:', err);
    });
    const express = require('express');
    const cors = require('cors');
    const path = require('path');
    const { initializeDatabase } = require('./server/database');
    const { fetchAllJobs } = require('./server/jobLogic');
    const app = express();
    const port = process.env.PORT || 8080;
    app.use(cors());
    app.use(express.json());
    app.get('/api/jobs', async (req, res) => {
      try {
        const jobs = await fetchAllJobs();
        res.json(jobs);
      } catch (error) {
        console.error('Error fetching jobs:', error);
        res.status(500).json({ error: 'Error fetching jobs' });
      }
    });
    app.use(express.static(path.join(__dirname, 'client/build')));
    app.get('/health', (req, res) => {
      res.status(200).send('OK');
    });
    app.get('*', (req, res) => {
      res.sendFile(path.join(__dirname, 'client/build', 'index.html'));
    });
    app.use((err, req, res, next) => {
      console.error(err.stack);
      res.status(500).send('Something broke!');
    });
    app.use((req, res, next) => {
      res.status(404).send("404 - Not Found");
    });
    initializeDatabase()
      .then(() => {
        console.log('Database initialized successfully');
        return new Promise((resolve) => {
          const server = app.listen(port, () => {
            console.log(`Server running at http://localhost:${port}`);
            resolve(server);
          });
        });
      })
      .then((server) => {
        console.log('Server started successfully');
        return fetchAllJobs();
      })
      .then(() => {
        console.log('Initial job fetch completed');
      })
      .catch(error => {
        console.error('Error during startup:', error);
        process.exit(1);
      });
    

    server/jobLogic.js:

    const { getConnection } = require('./database');
    async function fetchAllJobs() {
      const connection = getConnection();
      const [rows] = await connection.execute('SELECT * FROM jobs');
      return rows;
    }
    module.exports = {
      fetchAllJobs
    };
    

    Client/JobList.js:

    import React, { useState, useEffect } from 'react';
    function JobList() {
      const [jobs, setJobs] = useState([]);
      const [loading, setLoading] = useState(true);
      const [error, setError] = useState(null);
      useEffect(() => {
        async function fetchJobs() {
          try {
            const response = await fetch('https://kanodejamysqlapp.azurewebsites.net/api/jobs'); 
            if (!response.ok) {
              throw new Error('Network response was not ok');
            }
            const data = await response.json();
            setJobs(data);
          } catch (error) {
            setError(error);
          } finally {
            setLoading(false);
          }
        }
        fetchJobs();
      }, []);
      if (loading) return <p>Loading...</p>;
      if (error) return <p>Error fetching jobs: {error.message}</p>;
      return (
        <div>
          <ul>
            {jobs.map((job) => (
              <li key={job.id}>{job.title}</li>
            ))}
          </ul>
        </div>
      );
    }
    export default JobList;
    

    GitHub Workflow:

    name: Build and deploy Node.js app to Azure Web App - kanodejamysqlapp
    on:
      push:
        branches:
          - main
      workflow_dispatch:
    jobs:
      build:
        runs-on: ubuntu-latest
        steps:
          - uses: actions/checkout@v4
          - name: Set up Node.js version
            uses: actions/setup-node@v3
            with:
              node-version: '18.x'
          - name: Install backend dependencies
            run: npm install
          - name: Install frontend dependencies and build client
            run: |
              cd client
              npm install
              chmod +x node_modules/.bin/react-scripts
              npm run build
          - name: Zip artifact for deployment
            run: zip -r release.zip ./*
          - name: Upload artifact for deployment job
            uses: actions/upload-artifact@v4
            with:
              name: node-app
              path: release.zip
      deploy:
        runs-on: ubuntu-latest
        needs: build
        environment:
          name: 'Production'
        steps:
          - name: Download artifact from build job
            uses: actions/download-artifact@v4
            with:
              name: node-app
          - name: Unzip artifact for deployment
            run: unzip release.zip
          - name: Deploy to Azure Web App
            id: deploy-to-webapp
            uses: azure/webapps-deploy@v3
            with:
              app-name: 'kanodejamysqlapp'
              slot-name: 'Production'
              package: .
              publish-profile: ${{ secrets.AZUREAPPSERVICE_PUBLISHPROFILE_<secret_key> }}
    

    Azure App Service Output:

    enter image description here

    Login or Signup to reply.
  2. From the error message it states that the main issue is originating from /home/site/wwwroot/server.js and that looks to be at the root of you project.

    There could be high possibility that package.json is missing in this
    root level.

    So, either you create a new package.json in the root of your project that has all the packages required in the server.js or move you existing package.json to root level.

       /node_modules
       /client
       /server.js
       /package.json
    

    And since the GitHub Actions Workflow is already doing a npm ci at root level hopefully this should server the server.js on port 8080.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search