The Ownstak configuration file (ownstak.config.mjs
) allows you to customize how your project is built, deployed and store this config together with your project source code. This file should be placed in your project's root directory. If no file is found, the CLI uses default or auto-detected values.
You can create a new config for your project by running:
- NPM
- PNPM
- Yarn
- Bun
npx ownstak config init
pnpm dlx ownstak config init
yarn dlx ownstak config init
bunx ownstak config init
This command will launch a wizard to guide you through the setup. Other supported file names include ownstak.config.js
, ownstak.config.cjs
, and ownstak.config.ts
.
Basic Example
Here's a basic example of an Ownstak configuration file:
import { Config } from 'ownstak';
export default new Config()
.setOrganization("my-org")
.setProject("my-next-app")
.setRuntime("nodejs22.x")
.setArch("arm64");
The configuration file is evaluated only once at build time, which means you can configure it programmatically or use environment variables from your CI/CD pipelines in it:
import { Config } from 'ownstak';
export default new Config().setRuntime(process.env.OWNSTAK_RUNTIME)
Basic Options
setProject
Sets the name of your project (project
). This name is later displayed in the OwnStak Console.
By default, the project name from package.json
is used.
If the project doesn't exist in the given organization, the CLI will create it on deploy.
- Default: Name from
package.json
or'default'
- Type:
.setProject(name: string)
setOrganization
Sets the name of your organization (organization
) in the OwnStak Console.
The organization needs to exist; otherwise, deployment fails.
- Default: Name from
package.json
or'default'
- Type:
.setOrganization(name: string)
setEnvironment
Sets the environment name (environment
) for your deployment that is later also displayed in the OwnStak Console.
Defaults to default
. If the environment doesn't exist in the given organization and project, the CLI will create it on deploy.
- Default:
'default'
- Type:
.setEnvironment(name: string)
setRuntime
Sets the Node.js runtime version (runtime
) to use for your application.
- Default: Automatically selected based on your local Node.js version
- Supported Values:
'nodejs18.x'
,'nodejs20.x'
,'nodejs22.x'
- Type:
.setRuntime(runtime: string)
setMemory
Sets the amount of RAM (memory
) in MiB to allocate to your application.
- Default:
1024
- Range: 1–10240 MiB
- Type:
.setMemory(sizeInMiB: number)
setArch
Sets the CPU architecture (arch
) to use for your application.
- Default: Automatically selected based on your local architecture
- Supported Values:
'x86_64'
,'arm64'
- Type:
.setArch(architecture: string)
setTimeout
Sets the maximum execution time (timeout
) in seconds for your application.
- Default:
20
- Range: 1–900 seconds
- Type:
.setTimeout(durationInSeconds: number)
setFramework
Sets the framework (framework
) to use for your application.
The OwnStak CLI comes with support for predefined frameworks and will auto-detect supported frameworks during the npx ownstak deploy
or npx ownstak build
commands.
If you want to deploy a custom project type, set the framework to custom
and see the Custom framework guide.
- Default: Auto-detected framework
- Supported Values:
'nextjs'
,'astrojs'
,'static'
,'custom'
- Type:
.setFramework(framework: string)
Advanced Options
includeApp
Includes application files (app
) and runtime dependencies. Use this to include or exclude additional files in your build, such as dynamically loaded dependencies, server-side code, or custom config files that your app requires.
- Type:
.includeApp(path: string, destination?: string | boolean)
Examples:
// Include a single file under the same name
.includeApp("my-config.json")
// Include files with glob pattern under the same name
.includeApp("src/**/*.{json,yml}")
// Include files into custom destination
.includeApp("src/**/*.{json}", "dist/**/*")
// Include all files from src folder and exclude only json files
.includeApp("src/**/*")
.includeApp("src/**/*.{json}", false)
includeAsset
Includes static assets (assets
) - static files that don't contain a hash in their name and can change between deployments, e.g., index.html
.
This option is usually configured by the frameworkAdapter
.
The path can contain files, directories, or glob patterns that are absolute or relative to the project source directory. The destination defines the target destination inside the build directory. Use true
to include the asset under the same path as the source, false
to exclude it, or define a custom path as a string.
- Type:
.includeAsset(path, destination?)
Examples:
// Include a single file under the same name
.includeAsset("index.html")
// Include entire directory into custom destination
.includeAsset("./public", "./")
// Include files with glob patterns
.includeAsset("dist/**/*.{html,css,js}")
// Include with custom destination
.includeAsset("src/assets", "public/assets")
// Include all files in public folder and exclude just files in the public/temp/ folder
.includeAsset("public/**/*")
.includeAsset("public/temp/**/*", false)
includePermanentAsset
Includes permanent static assets (permanentAssets
) - files that contain a content hash in their name and are expected to never change, e.g., chunk-asdf123.js
.
This option is usually configured by the frameworkAdapter
. It uses the same syntax format as includeAsset
.
- Type:
.includePermanentAsset(path, destination?)
includeDebugAsset
Includes debug assets (debugAssets
) that are included during development or debugging builds.
These assets are typically used for debugging purposes and may include source maps, debug logs, or development-specific files. It uses the same syntax format as includeAsset
.
- Type:
.includeDebugAsset(path, destination?)
setAppEntrypoint
Sets the entry point (app.entrypoint
) for your application. This entrypoint should start the HTTP server on process.env.PORT
with your application.
Optionally, the app entrypoint can export a function as the default export that starts the server and returns a promise that resolves when the server is ready to accept requests.
- Type:
.setAppEntrypoint(entrypoint: string)
Examples:
// Basic Express.js server
.setAppEntrypoint("./server.js")
setCopyAppDependencies
Controls whether to trace and copy all your app entrypoint dependencies (app.copyDependencies
) during the build.
When enabled, OwnStak automatically analyzes your entrypoint file and includes all required dependencies.
This includes node_modules
, source files, and any files your application imports.
This option saves you time, so you don't need to manually include all required node_modules into the build.
You still might need to include all dependencies that your app dynamically reads. For example, config.json
files, etc.
- Default:
false
- Type:
.setCopyAppDependencies(value: boolean)
setBundleAppDependencies
Controls whether to bundle all your app entrypoint dependencies (app.bundleDependencies
) during the build.
The bundling process will include all dependencies into your resulting entrypoint file, which results in faster startup times
but may not work for all dependency/app types. The output format (ESM/CJS) is selected based on the input format.
- Default:
false
- Type:
.setBundleAppDependencies(value: boolean)
setFrameworkAdapter
Sets the framework adapter (frameworkAdapter
) that defines how to build and deploy your application.
The CLI comes with predefined adapters for supported frameworks, but this option allows you to write your own support for any framework or tweak the existing behavior by hooking into each build phase.
- Default: Auto-detected framework adapter
- Type:
.setFrameworkAdapter(adapter: FrameworkAdapter)
setSkipFrameworkBuild
Sets whether to skip the framework build (skipFrameworkBuild
) and use existing build output when npx ownstak build
or npx ownstak deploy
commands are called.
- Default:
false
- Type:
.setSkipFrameworkBuild(skip: boolean = true)
setBuildCommand
Sets the build command (buildCommand
) that should be executed during the build process when running npx ownstak build
or npx ownstak deploy
. This option allows you to customize how your application is built or integrate with your existing build workflow.
For example, set it to npx docusaurus build
to build and deploy your documentation site with a single command.
OwnStak comes with predefined build commands for supported frameworks. Use this option if you want to use a different build command for your Next.js framework.
- Default: Framework-specific build command (e.g.,
npx next build
for Next.js) orundefined
forcustom
andstatic
frameworks - Type:
.setBuildCommand(command: string)
setDevCommand
Sets the dev command (devCommand
) that should be executed when running npx ownstak dev
to start your development server. This option allows you to customize how your application runs in development mode or integrate with your existing development workflow.
For example, set it to npx docusaurus start
to start your documentation site in development mode.
OwnStak comes with predefined dev commands for supported frameworks. Use this option if you want to use a different dev command for your Next.js framework.
- Default: Framework-specific dev command (e.g.,
npx next dev
for Next.js) orundefined
forcustom
andstatic
frameworks - Type:
.setDevCommand(command: string)
setDefaultFile
Sets the default file (assets.defaultFile
or permanentAssets.defaultFile
) to serve when no route matches.
Set this option to index.html
asset if your static SPA app serves the same index.html
file for all paths.
Set this option to 404.html
asset if your static MPA app serves only known paths and 404.html
file for everything else.
- Type:
.setDefaultFile(filePath: string)
setDefaultStatus
Sets the default HTTP status code for unmatched routes (for both assets.defaultStatus
and permanentAssets.defaultStatus
).
Set this option to 200
status code if your static SPA app serves the same index.html
file for all paths.
Set this option to 404
status code if your static MPA app serves only known paths and 404.html
file for everything else.
- Type:
.setDefaultStatus(statusCode: number)
setConvertHtmlToFolders
Controls whether to convert all .html files to folder format with index.html inside (for both assets.convertHtmlToFolders
and permanentAssets.convertHtmlToFolders
).
For example, /about.html
file will become accessible at /about
.
- Default:
false
- Type:
.setConvertHtmlToFolders(value: boolean)
setRedirect
Sets up HTTP redirects (redirects
) for your application. Useful for redirecting old URLs to new ones, maintaining SEO rankings, and ensuring users reach the correct content.
- Default statusCode:
302
- Type:
.setRedirect(from, to, statusCode?)
Examples:
// Basic redirect (302)
.setRedirect('/old-page', '/new-page')
// Permanent redirect (301)
.setRedirect('/legacy-blog', '/new-blog', 301)
// Redirect with path parameters
.setRedirect('/blog/:slug', '/new-blog/:slug', 301)
// Redirect with wildcard paths
.setRedirect('/docs/v1/:path*', '/docs/v2/:path*', 308)
// Complex condition redirect
.setRedirect({
path: /^\/old-section\/.*$/,
method: 'GET'
}, '/new-section', 301)
setResponseHeaders
Sets custom HTTP response headers (responseHeaders
) for your application. Useful for cache control, security headers, CORS, and other custom headers.
- Type:
.setResponseHeaders(headers, path?)
Examples:
// Set headers for all paths
.setResponseHeaders({
"X-Frame-Options": "DENY",
"X-Content-Type-Options": "nosniff",
"Cache-Control": "public, max-age=31536000"
})
// Set headers for specific paths
.setResponseHeaders({ "Cache-Control": "public, max-age=31536000" }, "/assets/:path*")
.setResponseHeaders({ "Cache-Control": "no-cache" }, {
path: /\.html$/,
method: "GET"
})
setResponseStatus
Sets the HTTP status code (responseStatus
) for responses. Primarily used for static sites to control how 404 pages are handled.
- Default:
200
- Type:
.setResponseStatus(status: number)
setRouter
Sets the internal Router that allows you to define more complex routing logic for your project. This configuration option is not recommended for end-users.
- Type:
.setRouter(router: Router)
Methods Example
The Config
provides several methods for programmatically setting configuration values in your own code.
Here's an example of all available methods:
import { Config } from 'ownstak';
export default new Config()
.setOrganization('my-org')
.setProject('my-app')
.setEnvironment('production')
.setRuntime('nodejs20')
.setMemory(2048)
.setArch('x86_64')
.setTimeout(30)
.setFramework('custom')
.includeAsset('./public', './')
.includePermanentAsset('./static')
.includeDebugAsset('./debug')
.includeApp('./dist/server.js', './server.js')
.setDevCommand('npx vite dev')
.setBuildCommand('npx vite build')
.setAppEntrypoint('./server.js')
.setCopyAppDependencies(true)
.setBundleAppDependencies(true)
.setConvertHtmlToFolders(true)
.setSkipFrameworkBuild(true)
.setDefaultStatus(200)
.setDefaultFile('static/index.html')
.setFrameworkAdapter({
name: 'My custom framework',
hooks: {
'build:start': ({ config }) => {}, // Runs at the beginning of the build process
'build:routes:start': ({ config }) => {}, // Runs before any default routes are added
'build:routes:finish': ({ config }) => {}, // Runs after all routes are added
'build:finish': ({ config }) => {}, // Runs right before build completion
'dev:start': ({ config }) => {} // Runs when starting the development server
}
})
This is the default and recommended way to define your OwnStak project configuration.
Options Example
Here's a complete example showing all available options on Config object:
import { Config } from 'ownstak';
export default new Config({
project: 'my-custom-app',
organization: 'my-org',
environment: 'production',
runtime: 'nodejs20',
memory: 2048,
arch: 'x86_64',
timeout: 30,
framework: 'custom',
skipFrameworkBuild: false,
buildCommand: 'npx vite build',
devCommand: 'npx vite dev'
assets: {
convertHtmlToFolders: true,
defaultFile: 'static/index.html'.
defaultStatus: 200,
include: {
'./public': './',
'./static': true,
'./public/*.{js,css}': false
}
},
permanentAssets: {
convertHtmlToFolders: false,
defaultFile: 'static/index.html'.
defaultStatus: 200,
include: {
'./_astro': './'
}
},
debugAssets: {
include: {
'./debug': true
}
},
app: {
include: {
'./dist/server.js': './server.js'
},
entrypoint: './server.js',
copyDependencies: false,
bundleDependencies: false
},
frameworkAdapter: {
name: 'My custom framework',
hooks: {
'build:start': ({ config }) => {}, // Runs at the beginning of the build process
'build:routes:start': ({ config }) => {}, // Runs before any default routes are added
'build:routes:finish': ({ config }) => {}, // Runs after all routes are added
'build:finish': ({ config }) => {}, // Runs right before build completion
'dev:start': ({ config }) => {} // Runs when starting the development server
}
}
});
JSON Example
If you prefer not to install ownstak
as a project dependency or simply want to avoid using JavaScript/TypeScript, you can define the configuration using a plain JSON file:
{
"project": "my-nextjs-app",
"organization": "my-org"
}
Environment variables cannot be used with the JSON config.