Initial commit
This commit is contained in:
166
server.js
Normal file
166
server.js
Normal file
@@ -0,0 +1,166 @@
|
||||
import http from "http";
|
||||
|
||||
import { readdir } from "fs/promises";
|
||||
import { stat } from "fs/promises";
|
||||
import { readFile } from "fs/promises";
|
||||
import { join } from "path";
|
||||
import { dirname } from "path";
|
||||
import { fileURLToPath } from "url";
|
||||
|
||||
|
||||
class App
|
||||
{
|
||||
|
||||
|
||||
constructor( )
|
||||
{
|
||||
|
||||
const selfPath = fileURLToPath( import.meta.url );
|
||||
|
||||
this.rootPath = dirname( selfPath );
|
||||
this.httpServer = null;
|
||||
|
||||
}
|
||||
|
||||
|
||||
async start( )
|
||||
{
|
||||
|
||||
this.httpServer = http.createServer( this.handleRequest.bind( this ) );
|
||||
|
||||
this.httpServer.listen( 3000 );
|
||||
|
||||
}
|
||||
|
||||
|
||||
async handleRequest( req, res )
|
||||
{
|
||||
|
||||
const requestedPath = decodeURI( req.url );
|
||||
const fullPath = join( this.rootPath, requestedPath );
|
||||
|
||||
const exists = await this.checkFileExists( fullPath );
|
||||
|
||||
if ( !exists )
|
||||
{
|
||||
|
||||
res.statusCode = 404;
|
||||
res.end( "Not Found" );
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
const stats = await stat( fullPath );
|
||||
|
||||
if ( stats.isDirectory( ) )
|
||||
{
|
||||
|
||||
const indexPath = join( fullPath, "index.html" );
|
||||
const indexExists = await this.checkFileExists( indexPath );
|
||||
|
||||
if ( indexExists )
|
||||
{
|
||||
|
||||
await this.sendFile( indexPath, res );
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
await this.sendDirectoryListing( fullPath, requestedPath, res );
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
await this.sendFile( fullPath, res );
|
||||
|
||||
}
|
||||
|
||||
|
||||
async sendFile( path, res )
|
||||
{
|
||||
|
||||
const contentType = this.getContentType( path );
|
||||
const fileData = await readFile( path );
|
||||
|
||||
res.setHeader( "Content-Type", contentType );
|
||||
res.statusCode = 200;
|
||||
|
||||
res.end( fileData );
|
||||
|
||||
}
|
||||
|
||||
|
||||
async sendDirectoryListing( dirPath, urlPath, res )
|
||||
{
|
||||
|
||||
const entries = await readdir( dirPath, { withFileTypes : true } );
|
||||
|
||||
let html = "<html><body><h1>Index of " + urlPath + "</h1><ul>";
|
||||
|
||||
let i = 0;
|
||||
|
||||
while ( i < entries.length )
|
||||
{
|
||||
|
||||
const e = entries[ i ].name;
|
||||
const link = urlPath.endsWith( "/" )
|
||||
? urlPath + e
|
||||
: urlPath + "/" + e;
|
||||
|
||||
html = html + "<li><a href=\"" + link + "\">" + e + "</a></li>";
|
||||
|
||||
i = i + 1;
|
||||
|
||||
}
|
||||
|
||||
html = html + "</ul></body></html>";
|
||||
|
||||
res.setHeader( "Content-Type", "text/html" );
|
||||
res.statusCode = 200;
|
||||
|
||||
res.end( html );
|
||||
|
||||
}
|
||||
|
||||
|
||||
async checkFileExists( path )
|
||||
{
|
||||
|
||||
const exists = await stat( path )
|
||||
.then( function( ) { return true; } )
|
||||
.catch( function( ) { return false; } );
|
||||
|
||||
return exists;
|
||||
|
||||
}
|
||||
|
||||
|
||||
getContentType( path )
|
||||
{
|
||||
|
||||
const lower = path.toLowerCase( );
|
||||
|
||||
if ( lower.endsWith( ".html" ) ) return "text/html";
|
||||
if ( lower.endsWith( ".css" ) ) return "text/css";
|
||||
if ( lower.endsWith( ".js" ) ) return "text/javascript";
|
||||
if ( lower.endsWith( ".json" ) ) return "application/json";
|
||||
if ( lower.endsWith( ".wasm" ) ) return "application/wasm";
|
||||
if ( lower.endsWith( ".png" ) ) return "image/png";
|
||||
if ( lower.endsWith( ".jpg" ) ) return "image/jpeg";
|
||||
if ( lower.endsWith( ".jpeg" ) ) return "image/jpeg";
|
||||
if ( lower.endsWith( ".gif" ) ) return "image/gif";
|
||||
if ( lower.endsWith( ".svg" ) ) return "image/svg+xml";
|
||||
if ( lower.endsWith( ".wgsl" ) ) return "text/plain";
|
||||
if ( lower.endsWith( ".txt" ) ) return "text/plain";
|
||||
|
||||
return "application/octet-stream";
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
const app = new App( );
|
||||
|
||||
await app.start( );
|
||||
Reference in New Issue
Block a user