Skip to content

Commit

Permalink
Merge pull request #300 from lastmjs/spa-root
Browse files Browse the repository at this point in the history
add spa root
  • Loading branch information
lastmjs authored Feb 7, 2020
2 parents 808f162 + 39449a2 commit b066c73
Show file tree
Hide file tree
Showing 18 changed files with 74 additions and 48 deletions.
8 changes: 8 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -689,6 +689,14 @@ A comma-separated list of paths, relative to the current directory, to include i
--include [include]
```

### SPA Root

A path to a file, relative to the current directory, to serve as the SPA root. It will be returned for the root path and when a file cannot be found:

```bash
--spa-root [spaRoot]
```

### Disable SPA

Disable the SPA redirect to index.html:
Expand Down
1 change: 1 addition & 0 deletions index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ export type CommandLineOptions = {
readonly customHTTPHeadersFilePath: string | undefined;
readonly ascOptionsFilePath: string | undefined;
readonly tscOptionsFilePath: string | undefined;
readonly spaRoot: string | undefined;
};

export type Clients = {
Expand Down
7 changes: 4 additions & 3 deletions src/app.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import {
start,
startStaticBuild
} from './zwitterion.ts';
import { commandLineOptions } from './command-line.ts';
} from './zwitterion';
import { commandLineOptions } from './command-line';

(async () => {

Expand All @@ -13,7 +13,8 @@ import { commandLineOptions } from './command-line.ts';
disableSpa: commandLineOptions.disableSpa,
customHTTPHeadersFilePath: commandLineOptions.customHTTPHeadersFilePath,
ascOptionsFilePath: commandLineOptions.ascOptionsFilePath,
tscOptionsFilePath: commandLineOptions.tscOptionsFilePath
tscOptionsFilePath: commandLineOptions.tscOptionsFilePath,
spaRoot: commandLineOptions.spaRoot
});

// TODO we might want to make the static builder take care of setting up and tearing down its own Zwitterion instance
Expand Down
7 changes: 5 additions & 2 deletions src/command-line.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import * as program from 'commander';
import * as fs from 'fs-extra';
import { CommandLineOptions } from '../index.d.ts';
import { CommandLineOptions } from '../index.d';

const packageJSON: {
version: string;
Expand All @@ -19,6 +19,7 @@ program
.option('--headers-file [headersFile]', 'A path to a JSON file, relative to the current directory, for custom HTTP headers')
.option('--asc-options-file [ascOptionsFile]', 'A path to a JSON file, relative to the current directory, for asc compiler options')
.option('--tsc-options-file [tscOptionsFile]', 'A path to a JSON file, relative to the current directory, for tsc compiler options')
.option('--spa-root [spaRoot]', 'A path to a file, relative to the current directory, to serve as the SPA root. It will be returned for the root path and when a file cannot be found')
// .options('--plugins [plugins]', '')
.parse(process.argv);

Expand All @@ -33,6 +34,7 @@ const disableSpa: boolean = program.disableSpa || false;
const customHTTPHeadersFilePath: string | undefined = program.headersFile;
const ascOptionsFilePath: string | undefined = program.ascOptionsFile;
const tscOptionsFilePath: string | undefined = program.tscOptionsFile;
const spaRoot: string | undefined = program.spaRoot;

export const commandLineOptions: Readonly<CommandLineOptions> = {
buildStatic,
Expand All @@ -44,5 +46,6 @@ export const commandLineOptions: Readonly<CommandLineOptions> = {
disableSpa,
customHTTPHeadersFilePath,
ascOptionsFilePath,
tscOptionsFilePath
tscOptionsFilePath,
spaRoot
};
28 changes: 19 additions & 9 deletions src/http-server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,15 +6,15 @@ import {
CustomHTTPHeaders,
HTTPHeaders,
Plugin
} from '../index.d.ts';
} from '../index.d';
import {
getFileContents,
getCustomHTTPHeaders,
getCustomHTTPHeadersForURL,
getCompilerOptionsFromFile
} from './utilities.ts';
} from './utilities';
import * as mime from 'mime';
import { ZwitterionPlugins } from './plugins.ts';
import { ZwitterionPlugins } from './plugins';

export async function createHTTPServer(params: {
wsPort: number;
Expand All @@ -25,6 +25,7 @@ export async function createHTTPServer(params: {
customHTTPHeadersFilePath: string | undefined;
ascOptionsFilePath: string | undefined;
tscOptionsFilePath: string | undefined;
spaRoot: string | undefined;
}): Promise<Readonly<http.Server>> {
return http.createServer(async (req: Readonly<http.IncomingMessage>, res: http.ServerResponse) => {

Expand All @@ -38,6 +39,7 @@ export async function createHTTPServer(params: {
if (fileExtension === '/') {

await handleIndex({
spaRoot: params.spaRoot,
compiledFiles: params.compiledFiles,
watchFiles: params.watchFiles,
clients: params.clients,
Expand Down Expand Up @@ -68,7 +70,8 @@ export async function createHTTPServer(params: {
fileExtension,
tscOptionsFilePath: params.tscOptionsFilePath,
ascOptionsFilePath: params.ascOptionsFilePath
})
}),
spaRoot: params.spaRoot
});

return;
Expand All @@ -82,7 +85,8 @@ export async function createHTTPServer(params: {
clients: params.clients,
disableSpa: params.disableSpa,
res,
customHTTPHeadersFilePath: params.customHTTPHeadersFilePath
customHTTPHeadersFilePath: params.customHTTPHeadersFilePath,
spaRoot: params.spaRoot
});
}
catch(error) {
Expand Down Expand Up @@ -113,6 +117,7 @@ function getCompilerOptionsFilePath(params: {
}

async function handleIndex(params: {
spaRoot: string | undefined;
compiledFiles: CompiledFiles;
watchFiles: boolean;
clients: Clients;
Expand All @@ -121,15 +126,16 @@ async function handleIndex(params: {
customHTTPHeadersFilePath: string | undefined;
}): Promise<void> {

const url: string = './index.html';
const url: string = params.spaRoot === undefined ? './index.html' : `./${params.spaRoot}`;

const indexFileContentsResult: Readonly<FileContentsResult> = await getFileContents({
url,
compiledFiles: params.compiledFiles,
watchFiles: params.watchFiles,
clients: params.clients,
disableSpa: params.disableSpa,
transformer: 'NOT_SET'
transformer: 'NOT_SET',
spaRoot: params.spaRoot
});

const customHTTPHeaders: Readonly<CustomHTTPHeaders> = await getCustomHTTPHeaders({
Expand Down Expand Up @@ -164,6 +170,7 @@ async function handlePlugin(params: {
res: http.ServerResponse;
customHTTPHeadersFilePath: string | undefined;
compilerOptionsFilePath: string | undefined;
spaRoot: string | undefined;
}): Promise<void> {

// TODO can't we do better here than any?
Expand All @@ -185,7 +192,8 @@ async function handlePlugin(params: {
url: params.url,
compilerOptions,
wsPort: params.wsPort
})
}),
spaRoot: params.spaRoot
});

const customHTTPHeaders: Readonly<CustomHTTPHeaders> = await getCustomHTTPHeaders({
Expand Down Expand Up @@ -216,6 +224,7 @@ async function handleGeneric(params: {
disableSpa: boolean;
res: http.ServerResponse;
customHTTPHeadersFilePath: string | undefined;
spaRoot: string | undefined;
}): Promise<void> {

const genericFileContentsResult: Readonly<FileContentsResult> = await getFileContents({
Expand All @@ -224,7 +233,8 @@ async function handleGeneric(params: {
watchFiles: params.watchFiles,
clients: params.clients,
disableSpa: params.disableSpa,
transformer: 'NOT_SET'
transformer: 'NOT_SET',
spaRoot: params.spaRoot
});

const mimeType: string | null = mime.getType(params.url);
Expand Down
4 changes: 2 additions & 2 deletions src/languages/c++.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import {
Plugin
} from "../../index.d.ts";
import { CPlugin } from './c.ts';
} from "../../index.d";
import { CPlugin } from './c';

export const CPPPlugin: Readonly<Plugin> = {
fileExtensions: ['cpp', 'c++', 'cc'],
Expand Down
4 changes: 2 additions & 2 deletions src/languages/c.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
import {
Plugin,
COptions
} from "../../index.d.ts";
} from "../../index.d";
import { exec } from 'child_process';
import * as sanitize from 'sanitize-filename';
import {
addGlobals
} from '../utilities.ts';
} from '../utilities';
import * as fs from 'fs-extra';
import * as path from 'path';

Expand Down
2 changes: 1 addition & 1 deletion src/languages/json.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import {
Plugin,
JSONOptions
} from "../../index.d.ts";
} from "../../index.d";
import {
addGlobals
} from '../utilities';
Expand Down
4 changes: 2 additions & 2 deletions src/languages/jsx.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import {
Plugin
} from '../../index.d.ts';
import { JavaScriptPlugin } from './javascript.ts';
} from '../../index.d';
import { JavaScriptPlugin } from './javascript';

export const JSXPlugin: Readonly<Plugin> = {
fileExtensions: ['jsx'],
Expand Down
2 changes: 1 addition & 1 deletion src/languages/rust.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import {
Plugin,
RustCOptions
} from '../../index.d.ts';
} from '../../index.d';
import {
addGlobals
} from '../utilities';
Expand Down
4 changes: 2 additions & 2 deletions src/languages/tsx.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import {
Plugin
} from '../../index.d.ts';
import { JavaScriptPlugin } from './javascript.ts';
} from '../../index.d';
import { JavaScriptPlugin } from './javascript';

export const TSXPlugin: Readonly<Plugin> = {
fileExtensions: ['tsx'],
Expand Down
4 changes: 2 additions & 2 deletions src/languages/typescript.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import {
Plugin
} from '../../index.d.ts';
import { JavaScriptPlugin } from './javascript.ts';
} from '../../index.d';
import { JavaScriptPlugin } from './javascript';

export const TypeScriptPlugin: Readonly<Plugin> = {
fileExtensions: ['ts'],
Expand Down
2 changes: 1 addition & 1 deletion src/languages/wasm.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import {
Plugin
} from '../../index.d.ts';
} from '../../index.d';
import {
addGlobals
} from '../utilities';
Expand Down
2 changes: 1 addition & 1 deletion src/languages/wat.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import {
Plugin,
WabtOptions
} from '../../index.d.ts';
} from '../../index.d';
import {
addGlobals
} from '../utilities';
Expand Down
24 changes: 12 additions & 12 deletions src/plugins.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,16 @@
import { Plugin } from "../index.d.ts";
import { Plugin } from "../index.d";

import { JavaScriptPlugin } from './languages/javascript.ts';
import { TypeScriptPlugin } from './languages/typescript.ts';
import { JSONPlugin } from './languages/json.ts';
import { JSXPlugin } from './languages/jsx.ts';
import { TSXPlugin } from './languages/tsx.ts';
import { AssemblyScriptPlugin } from './languages/assemblyscript.ts';
import { RustPlugin } from './languages/rust.ts';
import { WatPlugin } from './languages/wat.ts';
import { WasmPlugin } from './languages/wasm.ts';
import { CPlugin } from './languages/c.ts';
import { CPPPlugin } from './languages/c++.ts';
import { JavaScriptPlugin } from './languages/javascript';
import { TypeScriptPlugin } from './languages/typescript';
import { JSONPlugin } from './languages/json';
import { JSXPlugin } from './languages/jsx';
import { TSXPlugin } from './languages/tsx';
import { AssemblyScriptPlugin } from './languages/assemblyscript';
import { RustPlugin } from './languages/rust';
import { WatPlugin } from './languages/wat';
import { WasmPlugin } from './languages/wasm';
import { CPlugin } from './languages/c';
import { CPPPlugin } from './languages/c++';

// TODO this is where we can load external plugins, then add them to the array

Expand Down
5 changes: 3 additions & 2 deletions src/utilities.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import {
HTTPHeaders,
FileContentsResult,
TSCOptions
} from '../index.d.ts';
} from '../index.d';
import * as chokidar from 'chokidar';
import * as WebSocket from 'ws';
import * as tsc from 'typescript';
Expand All @@ -24,6 +24,7 @@ export async function getFileContents(params: {
watchFiles: boolean;
clients: Clients;
transformer: Transformer | 'NOT_SET';
spaRoot: string | undefined;
}): Promise<Readonly<FileContentsResult>> {

const cachedFileContents: Readonly<Buffer> | null | undefined = await returnFileContentsFromCache({
Expand Down Expand Up @@ -64,7 +65,7 @@ export async function getFileContents(params: {
}

if (!params.disableSpa) {
const indexFileContents: Readonly<Buffer> = await fs.readFile(`./index.html`);
const indexFileContents: Readonly<Buffer> = await fs.readFile(params.spaRoot === undefined ? `./index.html` : `./${params.spaRoot}`);

return {
fileContents: indexFileContents
Expand Down
2 changes: 1 addition & 1 deletion src/ws-server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import * as WebSocket from 'ws';
import * as http from 'http';
import {
Clients
} from '../index.d.ts';
} from '../index.d';

export function createWebSocketServer(params: {
wsPort: number;
Expand Down
12 changes: 7 additions & 5 deletions src/zwitterion.ts
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
import {
Clients,
CompiledFiles
} from '../index.d.ts';
} from '../index.d';
import * as http from 'http';
import { createHTTPServer } from './http-server.ts';
import { createHTTPServer } from './http-server';
import * as WebSocket from 'ws';
import { createWebSocketServer } from './ws-server.ts';
import { createWebSocketServer } from './ws-server';
import {
buildStatic
} from './static-builder.ts';
} from './static-builder';

export let httpServer: Readonly<http.Server> | 'NOT_CREATED' = 'NOT_CREATED';
export let wsServer: Readonly<WebSocket.Server> | 'NOT_CREATED' = 'NOT_CREATED';
Expand All @@ -23,6 +23,7 @@ export function start(params: {
customHTTPHeadersFilePath: string | undefined;
ascOptionsFilePath: string | undefined;
tscOptionsFilePath: string | undefined;
spaRoot: string | undefined;
}): Promise<void> {
return new Promise(async (resolve) => {
httpServer = await createHTTPServer({
Expand All @@ -33,7 +34,8 @@ export function start(params: {
disableSpa: params.disableSpa,
customHTTPHeadersFilePath: params.customHTTPHeadersFilePath,
ascOptionsFilePath: params.ascOptionsFilePath,
tscOptionsFilePath: params.tscOptionsFilePath
tscOptionsFilePath: params.tscOptionsFilePath,
spaRoot: params.spaRoot
});

wsServer = createWebSocketServer({
Expand Down

0 comments on commit b066c73

Please sign in to comment.