rename frontendDist to prodFrontend?

This commit is contained in:
Lucas Nogueira 2024-02-02 11:12:12 -03:00
parent 835009771c
commit ef7394f085
No known key found for this signature in database
GPG Key ID: FFEA6C72E73482F1
40 changed files with 319 additions and 150 deletions

View File

@ -9,7 +9,7 @@ Restructured Tauri config per [RFC#5](https://github.com/tauri-apps/rfcs/blob/f3
- Removed `package` object. - Removed `package` object.
- Renamed `tauri` object to `app`. - Renamed `tauri` object to `app`.
- Moved `tauri.bundle` object to the top-level. - Moved `tauri.bundle` object to the top-level.
- Renamed `build.distDir` field to `frontendDist`. - Renamed `build.distDir` field to `prodFrontend`.
- Renamed `build.devPath` field to `devUrl` and will no longer accepts paths, it will only accept URLs. - Renamed `build.devPath` field to `devUrl` and will no longer accepts paths, it will only accept URLs.
- Moved `tauri.pattern` to `app.security.pattern`. - Moved `tauri.pattern` to `app.security.pattern`.
- Removed `tauri.bundle.updater` object, and its fields have been moved to the updater plugin under `plugins.updater` object. - Removed `tauri.bundle.updater` object, and its fields have been moved to the updater plugin under `plugins.updater` object.

View File

@ -10,7 +10,7 @@ use std::{
path::PathBuf, path::PathBuf,
}; };
use tauri_codegen::{context_codegen, ContextData}; use tauri_codegen::{context_codegen, ContextData};
use tauri_utils::config::{AppUrl, WebviewUrl}; use tauri_utils::config::ProdFrontend;
// TODO docs // TODO docs
/// A builder for generating a Tauri application context during compile time. /// A builder for generating a Tauri application context during compile time.
@ -82,11 +82,11 @@ impl CodegenContext {
let (config, config_parent) = tauri_codegen::get_config(&self.config_path)?; let (config, config_parent) = tauri_codegen::get_config(&self.config_path)?;
// rerun if changed // rerun if changed
match &config.build.frontend_dist { match &config.build.prod_frontend {
Some(AppUrl::Url(WebviewUrl::App(p))) => { Some(ProdFrontend::Dist(p)) => {
println!("cargo:rerun-if-changed={}", config_parent.join(p).display()); println!("cargo:rerun-if-changed={}", config_parent.join(p).display());
} }
Some(AppUrl::Files(files)) => { Some(ProdFrontend::Files(files)) => {
for path in files { for path in files {
println!( println!(
"cargo:rerun-if-changed={}", "cargo:rerun-if-changed={}",

View File

@ -15,7 +15,7 @@ use tauri_utils::acl::capability::Capability;
use tauri_utils::acl::plugin::Manifest; use tauri_utils::acl::plugin::Manifest;
use tauri_utils::acl::resolved::Resolved; use tauri_utils::acl::resolved::Resolved;
use tauri_utils::assets::AssetKey; use tauri_utils::assets::AssetKey;
use tauri_utils::config::{AppUrl, Config, PatternKind, WebviewUrl}; use tauri_utils::config::{Config, PatternKind, ProdFrontend};
use tauri_utils::html::{ use tauri_utils::html::{
inject_nonce_token, parse as parse_html, serialize_node as serialize_html_node, inject_nonce_token, parse as parse_html, serialize_node as serialize_html_node,
}; };
@ -157,24 +157,21 @@ pub fn context_codegen(data: ContextData) -> Result<TokenStream, EmbeddedAssetsE
options = options.with_csp(); options = options.with_csp();
} }
let assets = match &config.build.frontend_dist { let assets = match &config.build.prod_frontend {
Some(url) => match url { Some(url) => match url {
AppUrl::Url(url) => match url { ProdFrontend::Url(_url) => Default::default(),
WebviewUrl::External(_) | WebviewUrl::CustomProtocol(_) => Default::default(), ProdFrontend::Dist(path) => {
WebviewUrl::App(path) => { let assets_path = config_parent.join(path);
let assets_path = config_parent.join(path); if !assets_path.exists() {
if !assets_path.exists() { panic!(
panic!( "The `{}` configuration is set to `{:?}` but this path doesn't exist",
"The `{}` configuration is set to `{:?}` but this path doesn't exist", if dev { "devPath" } else { "distDir" },
if dev { "devPath" } else { "distDir" }, path
path )
)
}
EmbeddedAssets::new(assets_path, &options, map_core_assets(&options, target))?
} }
_ => unimplemented!(), EmbeddedAssets::new(assets_path, &options, map_core_assets(&options, target))?
}, }
AppUrl::Files(files) => EmbeddedAssets::new( ProdFrontend::Files(files) => EmbeddedAssets::new(
files files
.iter() .iter()
.map(|p| config_parent.join(p)) .map(|p| config_parent.join(p))

View File

@ -1,7 +1,7 @@
{ {
"$schema": "http://json-schema.org/draft-07/schema#", "$schema": "http://json-schema.org/draft-07/schema#",
"title": "Config", "title": "Config",
"description": "The Tauri configuration object. It is read from a file where you can define your frontend assets, configure the bundler and define a tray icon.\n\nThe configuration file is generated by the [`tauri init`](https://tauri.app/v1/api/cli#init) command that lives in your Tauri application source directory (src-tauri).\n\nOnce generated, you may modify it at will to customize your Tauri application.\n\n## File Formats\n\nBy default, the configuration is defined as a JSON file named `tauri.conf.json`.\n\nTauri also supports JSON5 and TOML files via the `config-json5` and `config-toml` Cargo features, respectively. The JSON5 file name must be either `tauri.conf.json` or `tauri.conf.json5`. The TOML file name is `Tauri.toml`.\n\n## Platform-Specific Configuration\n\nIn addition to the default configuration file, Tauri can read a platform-specific configuration from `tauri.linux.conf.json`, `tauri.windows.conf.json`, `tauri.macos.conf.json`, `tauri.android.conf.json` and `tauri.ios.conf.json` (or `Tauri.linux.toml`, `Tauri.windows.toml`, `Tauri.macos.toml`, `Tauri.android.toml` and `Tauri.ios.toml` if the `Tauri.toml` format is used), which gets merged with the main configuration object.\n\n## Configuration Structure\n\nThe configuration is composed of the following objects:\n\n- [`package`](#packageconfig): Package settings - [`app`](#appconfig): The Tauri config - [`build`](#buildconfig): The build configuration - [`plugins`](#pluginconfig): The plugins config\n\n```json title=\"Example tauri.config.json file\" { \"productName\": \"tauri-app\", \"version\": \"0.1.0\" \"build\": { \"beforeBuildCommand\": \"\", \"beforeDevCommand\": \"\", \"devUrl\": \"../dist\", \"frontendDist\": \"../dist\" }, \"app\": { \"security\": { \"csp\": null }, \"windows\": [ { \"fullscreen\": false, \"height\": 600, \"resizable\": true, \"title\": \"Tauri App\", \"width\": 800 } ] }, \"bundle\": {} } ```", "description": "The Tauri configuration object. It is read from a file where you can define your frontend assets, configure the bundler and define a tray icon.\n\nThe configuration file is generated by the [`tauri init`](https://tauri.app/v1/api/cli#init) command that lives in your Tauri application source directory (src-tauri).\n\nOnce generated, you may modify it at will to customize your Tauri application.\n\n## File Formats\n\nBy default, the configuration is defined as a JSON file named `tauri.conf.json`.\n\nTauri also supports JSON5 and TOML files via the `config-json5` and `config-toml` Cargo features, respectively. The JSON5 file name must be either `tauri.conf.json` or `tauri.conf.json5`. The TOML file name is `Tauri.toml`.\n\n## Platform-Specific Configuration\n\nIn addition to the default configuration file, Tauri can read a platform-specific configuration from `tauri.linux.conf.json`, `tauri.windows.conf.json`, `tauri.macos.conf.json`, `tauri.android.conf.json` and `tauri.ios.conf.json` (or `Tauri.linux.toml`, `Tauri.windows.toml`, `Tauri.macos.toml`, `Tauri.android.toml` and `Tauri.ios.toml` if the `Tauri.toml` format is used), which gets merged with the main configuration object.\n\n## Configuration Structure\n\nThe configuration is composed of the following objects:\n\n- [`package`](#packageconfig): Package settings - [`app`](#appconfig): The Tauri config - [`build`](#buildconfig): The build configuration - [`plugins`](#pluginconfig): The plugins config\n\n```json title=\"Example tauri.config.json file\" { \"productName\": \"tauri-app\", \"version\": \"0.1.0\" \"build\": { \"beforeBuildCommand\": \"\", \"beforeDevCommand\": \"\", \"devUrl\": \"../dist\", \"prodFrontend\": { \"dist\": \"../dist\" }, }, \"app\": { \"security\": { \"csp\": null }, \"windows\": [ { \"fullscreen\": false, \"height\": 600, \"resizable\": true, \"title\": \"Tauri App\", \"width\": 800 } ] }, \"bundle\": {} } ```",
"type": "object", "type": "object",
"properties": { "properties": {
"$schema": { "$schema": {
@ -1097,18 +1097,18 @@
] ]
}, },
"devUrl": { "devUrl": {
"description": "The URL to load in development.\n\nThis is usually an URL to a dev server, which serves your application assets with hot-reload and HMR. Most modern JavaScript bundlers like [vite](https://vitejs.dev/guide/) provides a way to start a dev server by default.\n\nIf you don't have a dev server or don't want to use one, ignore this option and use [`frontendDist`](BuildConfig::frontend_dist) and point to a web assets directory, and Tauri CLI will run its built-in dev server and provide a simple hot-reload experience.", "description": "The URL to load in development.\n\nThis is usually an URL to a dev server, which serves your application assets with hot-reload and HMR. Most modern JavaScript bundlers like [vite](https://vitejs.dev/guide/) provides a way to start a dev server by default.\n\nIf you don't have a dev server or don't want to use one, ignore this option and use [`prodFrontend`](BuildConfig::prod_frontend) and point to a web assets directory, and Tauri CLI will run its built-in dev server and provide a simple hot-reload experience.",
"type": [ "type": [
"string", "string",
"null" "null"
], ],
"format": "uri" "format": "uri"
}, },
"frontendDist": { "prodFrontend": {
"description": "The path to the application assets (usually the `dist` folder of your javascript bundler) or a URL that could be either a custom protocol registered in the tauri app (for example: `myprotocol://`) or a remote URL (for example: `https://site.com/app`).\n\nWhen a path relative to the configuration file is provided, it is read recursively and all files are embedded in the application binary. Tauri then looks for an `index.html` and serves it as the default entry point for your application.\n\nYou can also provide a list of paths to be embedded, which allows granular control over what files are added to the binary. In this case, all files are added to the root and you must reference it that way in your HTML files.\n\nWhen a URL is provided, the application won't have bundled assets and the application will load that URL by default.", "description": "The path to the application assets (usually the `dist` folder of your javascript bundler) or a URL that could be either a custom protocol registered in the tauri app (for example: `myprotocol://`) or a remote URL (for example: `https://site.com/app`).\n\nWhen a path relative to the configuration file is provided, it is read recursively and all files are embedded in the application binary. Tauri then looks for an `index.html` and serves it as the default entry point for your application.\n\nYou can also provide a list of paths to be embedded, which allows granular control over what files are added to the binary. In this case, all files are added to the root and you must reference it that way in your HTML files.\n\nWhen a URL is provided, the application won't have bundled assets and the application will load that URL by default.",
"anyOf": [ "anyOf": [
{ {
"$ref": "#/definitions/AppUrl" "$ref": "#/definitions/ProdFrontend"
}, },
{ {
"type": "null" "type": "null"
@ -1161,23 +1161,51 @@
}, },
"additionalProperties": false "additionalProperties": false
}, },
"AppUrl": { "ProdFrontend": {
"description": "Defines the URL or assets to embed in the application.", "description": "Defines the URL or assets to embed in the application.",
"anyOf": [ "oneOf": [
{ {
"description": "The app's external URL, or the path to the directory containing the app assets.", "description": "An external URL to load.",
"allOf": [ "type": "object",
{ "required": [
"$ref": "#/definitions/WebviewUrl" "url"
],
"properties": {
"url": {
"type": "string",
"format": "uri"
} }
] },
"additionalProperties": false
},
{
"description": "Path to the folder containing the frontend dist assets.",
"type": "object",
"required": [
"dist"
],
"properties": {
"dist": {
"type": "string"
}
},
"additionalProperties": false
}, },
{ {
"description": "An array of files to embed on the app.", "description": "An array of files to embed on the app.",
"type": "array", "type": "object",
"items": { "required": [
"type": "string" "files"
} ],
"properties": {
"files": {
"type": "array",
"items": {
"type": "string"
}
}
},
"additionalProperties": false
} }
] ]
}, },

View File

@ -1710,19 +1710,22 @@ fn default_min_sdk_version() -> u32 {
/// Defines the URL or assets to embed in the application. /// Defines the URL or assets to embed in the application.
#[derive(Debug, PartialEq, Eq, Clone, Deserialize, Serialize)] #[derive(Debug, PartialEq, Eq, Clone, Deserialize, Serialize)]
#[cfg_attr(feature = "schema", derive(JsonSchema))] #[cfg_attr(feature = "schema", derive(JsonSchema))]
#[serde(untagged, deny_unknown_fields)] #[serde(deny_unknown_fields, rename_all = "camelCase")]
#[non_exhaustive] #[non_exhaustive]
pub enum AppUrl { pub enum ProdFrontend {
/// The app's external URL, or the path to the directory containing the app assets. /// An external URL to load.
Url(WebviewUrl), Url(Url),
/// Path to the folder containing the frontend dist assets.
Dist(PathBuf),
/// An array of files to embed on the app. /// An array of files to embed on the app.
Files(Vec<PathBuf>), Files(Vec<PathBuf>),
} }
impl std::fmt::Display for AppUrl { impl std::fmt::Display for ProdFrontend {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self { match self {
Self::Url(url) => write!(f, "{url}"), Self::Url(url) => write!(f, "{url}"),
Self::Dist(p) => write!(f, "{}", p.display()),
Self::Files(files) => write!(f, "{}", serde_json::to_string(files).unwrap()), Self::Files(files) => write!(f, "{}", serde_json::to_string(files).unwrap()),
} }
} }
@ -1778,7 +1781,7 @@ pub struct BuildConfig {
/// This is usually an URL to a dev server, which serves your application assets with hot-reload and HMR. /// This is usually an URL to a dev server, which serves your application assets with hot-reload and HMR.
/// Most modern JavaScript bundlers like [vite](https://vitejs.dev/guide/) provides a way to start a dev server by default. /// Most modern JavaScript bundlers like [vite](https://vitejs.dev/guide/) provides a way to start a dev server by default.
/// ///
/// If you don't have a dev server or don't want to use one, ignore this option and use [`frontendDist`](BuildConfig::frontend_dist) /// If you don't have a dev server or don't want to use one, ignore this option and use [`prodFrontend`](BuildConfig::prod_frontend)
/// and point to a web assets directory, and Tauri CLI will run its built-in dev server and provide a simple hot-reload experience. /// and point to a web assets directory, and Tauri CLI will run its built-in dev server and provide a simple hot-reload experience.
#[serde(alias = "dev-url")] #[serde(alias = "dev-url")]
pub dev_url: Option<Url>, pub dev_url: Option<Url>,
@ -1796,7 +1799,7 @@ pub struct BuildConfig {
/// When a URL is provided, the application won't have bundled assets /// When a URL is provided, the application won't have bundled assets
/// and the application will load that URL by default. /// and the application will load that URL by default.
#[serde(alias = "frontend-dist")] #[serde(alias = "frontend-dist")]
pub frontend_dist: Option<AppUrl>, pub prod_frontend: Option<ProdFrontend>,
/// A shell command to run before `tauri dev` kicks in. /// A shell command to run before `tauri dev` kicks in.
/// ///
/// The TAURI_ENV_PLATFORM, TAURI_ENV_ARCH, TAURI_ENV_FAMILY, TAURI_ENV_PLATFORM_VERSION, TAURI_ENV_PLATFORM_TYPE and TAURI_ENV_DEBUG environment variables are set if you perform conditional compilation. /// The TAURI_ENV_PLATFORM, TAURI_ENV_ARCH, TAURI_ENV_FAMILY, TAURI_ENV_PLATFORM_VERSION, TAURI_ENV_PLATFORM_TYPE and TAURI_ENV_DEBUG environment variables are set if you perform conditional compilation.
@ -1922,7 +1925,9 @@ where
/// "beforeBuildCommand": "", /// "beforeBuildCommand": "",
/// "beforeDevCommand": "", /// "beforeDevCommand": "",
/// "devUrl": "../dist", /// "devUrl": "../dist",
/// "frontendDist": "../dist" /// "prodFrontend": {
/// "dist": "../dist"
/// },
/// }, /// },
/// "app": { /// "app": {
/// "security": { /// "security": {
@ -2003,7 +2008,7 @@ fn default_build() -> BuildConfig {
BuildConfig { BuildConfig {
runner: None, runner: None,
dev_url: None, dev_url: None,
frontend_dist: None, prod_frontend: None,
before_dev_command: None, before_dev_command: None,
before_build_command: None, before_build_command: None,
before_bundle_command: None, before_bundle_command: None,
@ -2335,14 +2340,19 @@ mod build {
} }
} }
impl ToTokens for AppUrl { impl ToTokens for ProdFrontend {
fn to_tokens(&self, tokens: &mut TokenStream) { fn to_tokens(&self, tokens: &mut TokenStream) {
let prefix = quote! { ::tauri::utils::config::AppUrl }; let prefix = quote! { ::tauri::utils::config::ProdFrontend };
tokens.append_all(match self { tokens.append_all(match self {
Self::Url(url) => { Self::Url(url) => {
let url = url_lit(url);
quote! { #prefix::Url(#url) } quote! { #prefix::Url(#url) }
} }
Self::Dist(path) => {
let path = path_buf_lit(path);
quote! { #prefix::Dist(#path) }
}
Self::Files(files) => { Self::Files(files) => {
let files = vec_lit(files, path_buf_lit); let files = vec_lit(files, path_buf_lit);
quote! { #prefix::Files(#files) } quote! { #prefix::Files(#files) }
@ -2354,7 +2364,7 @@ mod build {
impl ToTokens for BuildConfig { impl ToTokens for BuildConfig {
fn to_tokens(&self, tokens: &mut TokenStream) { fn to_tokens(&self, tokens: &mut TokenStream) {
let dev_url = opt_lit(self.dev_url.as_ref().map(url_lit).as_ref()); let dev_url = opt_lit(self.dev_url.as_ref().map(url_lit).as_ref());
let frontend_dist = opt_lit(self.frontend_dist.as_ref()); let prod_frontend = opt_lit(self.prod_frontend.as_ref());
let runner = quote!(None); let runner = quote!(None);
let before_dev_command = quote!(None); let before_dev_command = quote!(None);
let before_build_command = quote!(None); let before_build_command = quote!(None);
@ -2366,7 +2376,7 @@ mod build {
::tauri::utils::config::BuildConfig, ::tauri::utils::config::BuildConfig,
runner, runner,
dev_url, dev_url,
frontend_dist, prod_frontend,
before_dev_command, before_dev_command,
before_build_command, before_build_command,
before_bundle_command, before_bundle_command,
@ -2614,7 +2624,7 @@ mod test {
let build = BuildConfig { let build = BuildConfig {
runner: None, runner: None,
dev_url: None, dev_url: None,
frontend_dist: None, prod_frontend: None,
before_dev_command: None, before_dev_command: None,
before_build_command: None, before_build_command: None,
before_bundle_command: None, before_bundle_command: None,

View File

@ -292,11 +292,11 @@ impl<R: Runtime> AppManager<R> {
/// Get the base path to serve data from. /// Get the base path to serve data from.
/// ///
/// * In dev mode, this will be based on the `devUrl` configuration value. /// * In dev mode, this will be based on the `devUrl` configuration value.
/// * Otherwise, this will be based on the `frontendDist` configuration value. /// * Otherwise, this will be based on the `prodFrontend` configuration value.
#[cfg(not(dev))] #[cfg(not(dev))]
fn base_path(&self) -> Option<&Url> { fn base_path(&self) -> Option<&Url> {
use crate::{utils::config::AppUrl, WebviewUrl}; use crate::{utils::config::AppUrl, WebviewUrl};
match self.config.build.frontend_dist.as_ref() { match self.config.build.prod_frontend.as_ref() {
Some(AppUrl::Url(WebviewUrl::External(url) | WebviewUrl::CustomProtocol(url))) => Some(url), Some(AppUrl::Url(WebviewUrl::External(url) | WebviewUrl::CustomProtocol(url))) => Some(url),
_ => None, _ => None,
} }

View File

@ -1030,7 +1030,7 @@ fn main() {
&& current_url.domain() == protocol_url.domain() && current_url.domain() == protocol_url.domain()
}) || }) ||
// or if relative to `devUrl` or `frontendDist` // or if relative to `devUrl` or `prodFrontend`
self self
.manager() .manager()
.get_url() .get_url()

View File

@ -2,7 +2,9 @@
"$schema": "../../../../../core/tauri-config-schema/schema.json", "$schema": "../../../../../core/tauri-config-schema/schema.json",
"identifier": "studio.tauri.example", "identifier": "studio.tauri.example",
"build": { "build": {
"frontendDist": "../dist", "prodFrontend": {
"dist": "../dist"
},
"devUrl": "http://localhost:4000" "devUrl": "http://localhost:4000"
}, },
"app": { "app": {
@ -18,4 +20,4 @@
"bundle": { "bundle": {
"active": true "active": true
} }
} }

View File

@ -4,7 +4,9 @@
"version": "1.0.0", "version": "1.0.0",
"identifier": "com.tauri.api", "identifier": "com.tauri.api",
"build": { "build": {
"frontendDist": "../dist", "prodFrontend": {
"dist": "../dist"
},
"devUrl": "http://localhost:1420", "devUrl": "http://localhost:1420",
"beforeDevCommand": "yarn dev", "beforeDevCommand": "yarn dev",
"beforeBuildCommand": "yarn build" "beforeBuildCommand": "yarn build"
@ -22,7 +24,9 @@
"csp": { "csp": {
"default-src": "'self' customprotocol: asset:", "default-src": "'self' customprotocol: asset:",
"connect-src": "ipc: http://ipc.localhost", "connect-src": "ipc: http://ipc.localhost",
"font-src": ["https://fonts.gstatic.com"], "font-src": [
"https://fonts.gstatic.com"
],
"img-src": "'self' asset: http://asset.localhost blob: data:", "img-src": "'self' asset: http://asset.localhost blob: data:",
"style-src": "'unsafe-inline' 'self' https://fonts.googleapis.com" "style-src": "'unsafe-inline' 'self' https://fonts.googleapis.com"
}, },
@ -30,8 +34,13 @@
"assetProtocol": { "assetProtocol": {
"enable": true, "enable": true,
"scope": { "scope": {
"allow": ["$APPDATA/db/**", "$RESOURCE/**"], "allow": [
"deny": ["$APPDATA/db/*.stronghold"] "$APPDATA/db/**",
"$RESOURCE/**"
],
"deny": [
"$APPDATA/db/*.stronghold"
]
} }
} }
} }
@ -51,7 +60,11 @@
"name": "theme", "name": "theme",
"takesValue": true, "takesValue": true,
"description": "App theme", "description": "App theme",
"possibleValues": ["light", "dark", "system"] "possibleValues": [
"light",
"dark",
"system"
]
}, },
{ {
"short": "v", "short": "v",
@ -93,4 +106,4 @@
} }
} }
} }
} }

View File

@ -4,7 +4,11 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": ["index.html"] "prodFrontend": {
"files": [
"index.html"
]
}
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
@ -32,4 +36,4 @@
"../.icons/icon.ico" "../.icons/icon.ico"
] ]
} }
} }

View File

@ -2,7 +2,11 @@
"$schema": "../../../tooling/cli/schema.json", "$schema": "../../../tooling/cli/schema.json",
"identifier": "com.tauri.dev-file-associations-demo", "identifier": "com.tauri.dev-file-associations-demo",
"build": { "build": {
"frontendDist": ["../index.html"] "prodFrontend": {
"files": [
"../index.html"
]
}
}, },
"app": { "app": {
"security": { "security": {
@ -21,17 +25,24 @@
], ],
"fileAssociations": [ "fileAssociations": [
{ {
"ext": ["png"], "ext": [
"png"
],
"mimeType": "image/png" "mimeType": "image/png"
}, },
{ {
"ext": ["jpg", "jpeg"], "ext": [
"jpg",
"jpeg"
],
"mimeType": "image/jpeg" "mimeType": "image/jpeg"
}, },
{ {
"ext": ["gif"], "ext": [
"gif"
],
"mimeType": "image/gif" "mimeType": "image/gif"
} }
] ]
} }
} }

View File

@ -4,7 +4,11 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": ["index.html"] "prodFrontend": {
"files": [
"index.html"
]
}
}, },
"app": { "app": {
"windows": [ "windows": [
@ -31,4 +35,4 @@
"../.icons/icon.ico" "../.icons/icon.ico"
] ]
} }
} }

View File

@ -4,7 +4,9 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": "dist", "prodFrontend": {
"dist": "dist"
},
"beforeDevCommand": "", "beforeDevCommand": "",
"beforeBuildCommand": "" "beforeBuildCommand": ""
}, },
@ -40,4 +42,4 @@
"../.icons/icon.ico" "../.icons/icon.ico"
] ]
} }
} }

View File

@ -4,7 +4,11 @@
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"$schema": "../../core/tauri-config-schema/schema.json", "$schema": "../../core/tauri-config-schema/schema.json",
"build": { "build": {
"frontendDist": ["index.html"] "prodFrontend": {
"files": [
"index.html"
]
}
}, },
"app": { "app": {
"security": { "security": {
@ -22,4 +26,4 @@
"../.icons/icon.ico" "../.icons/icon.ico"
] ]
} }
} }

View File

@ -4,7 +4,11 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": ["index.html"] "prodFrontend": {
"files": [
"index.html"
]
}
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
@ -43,4 +47,4 @@
"copyright": "", "copyright": "",
"category": "DeveloperTool" "category": "DeveloperTool"
} }
} }

View File

@ -4,7 +4,9 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": "public" "prodFrontend": {
"dist": "public"
}
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
@ -32,4 +34,4 @@
"../.icons/icon.ico" "../.icons/icon.ico"
] ]
} }
} }

View File

@ -4,11 +4,14 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": ["index.html"] "prodFrontend": {
"files": [
"index.html"
]
}
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
"security": { "security": {
"csp": "default-src 'self'; connect-src ipc: http://ipc.localhost" "csp": "default-src 'self'; connect-src ipc: http://ipc.localhost"
} }
@ -24,4 +27,4 @@
"../.icons/icon.ico" "../.icons/icon.ico"
] ]
} }
} }

View File

@ -4,11 +4,14 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.resources", "identifier": "com.tauri.resources",
"build": { "build": {
"frontendDist": ["../index.html"] "prodFrontend": {
"files": [
"../index.html"
]
}
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
"windows": [ "windows": [
{ {
"title": "Welcome to Tauri!", "title": "Welcome to Tauri!",
@ -32,6 +35,8 @@
"../../.icons/icon.icns", "../../.icons/icon.icns",
"../../.icons/icon.ico" "../../.icons/icon.ico"
], ],
"resources": ["assets/*"] "resources": [
"assets/*"
]
} }
} }

View File

@ -4,7 +4,11 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": ["index.html"] "prodFrontend": {
"files": [
"index.html"
]
}
}, },
"app": { "app": {
"windows": [ "windows": [
@ -31,4 +35,4 @@
"../.icons/icon.ico" "../.icons/icon.ico"
] ]
} }
} }

View File

@ -4,7 +4,9 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": "dist" "prodFrontend": {
"dist": "dist"
}
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
@ -40,4 +42,4 @@
"../.icons/icon.ico" "../.icons/icon.ico"
] ]
} }
} }

View File

@ -4,7 +4,11 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": ["index.html"] "prodFrontend": {
"files": [
"index.html"
]
}
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
@ -32,4 +36,4 @@
"../.icons/icon.ico" "../.icons/icon.ico"
] ]
} }
} }

View File

@ -4,7 +4,11 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": ["index.html"] "prodFrontend": {
"files": [
"index.html"
]
}
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
@ -20,7 +24,9 @@
"security": { "security": {
"csp": "default-src 'self'; connect-src ipc: http://ipc.localhost; media-src stream: http://stream.localhost asset: http://asset.localhost", "csp": "default-src 'self'; connect-src ipc: http://ipc.localhost; media-src stream: http://stream.localhost asset: http://asset.localhost",
"assetProtocol": { "assetProtocol": {
"scope": ["**/test_video.mp4"] "scope": [
"**/test_video.mp4"
]
} }
} }
}, },
@ -35,4 +41,4 @@
"../.icons/icon.ico" "../.icons/icon.ico"
] ]
} }
} }

View File

@ -7,7 +7,9 @@
"beforeBuildCommand": "yarn build:tauri", "beforeBuildCommand": "yarn build:tauri",
"beforeDevCommand": "yarn dev:tauri", "beforeDevCommand": "yarn dev:tauri",
"devUrl": "http://localhost:5173", "devUrl": "http://localhost:5173",
"frontendDist": "../../build" "prodFrontend": {
"dist": "../../build"
}
}, },
"app": { "app": {
"security": { "security": {
@ -34,4 +36,4 @@
"../../../.icons/icon.ico" "../../../.icons/icon.ico"
] ]
} }
} }

View File

@ -4,7 +4,11 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.workspace", "identifier": "com.tauri.workspace",
"build": { "build": {
"frontendDist": ["../index.html"] "prodFrontend": {
"files": [
"../index.html"
]
}
}, },
"app": { "app": {
"security": { "security": {
@ -31,4 +35,4 @@
"../../.icons/icon.ico" "../../.icons/icon.ico"
] ]
} }
} }

View File

@ -2,7 +2,9 @@
"$schema": "../../../../../core/tauri-config-schema/schema.json", "$schema": "../../../../../core/tauri-config-schema/schema.json",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": "../public" "prodFrontend": {
"dist": "../public"
},
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
@ -30,4 +32,4 @@
"../../../../../examples/.icons/icon.ico" "../../../../../examples/.icons/icon.ico"
] ]
} }
} }

View File

@ -2,7 +2,9 @@
"$schema": "../../../../../core/tauri-config-schema/schema.json", "$schema": "../../../../../core/tauri-config-schema/schema.json",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": "../public" "prodFrontend": {
"dist": "../public"
},
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
@ -30,4 +32,4 @@
"../../../../../examples/.icons/icon.ico" "../../../../../examples/.icons/icon.ico"
] ]
} }
} }

View File

@ -2,7 +2,9 @@
"$schema": "../../../../../core/tauri-config-schema/schema.json", "$schema": "../../../../../core/tauri-config-schema/schema.json",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": "../public", "prodFrontend": {
"dist": "../public"
},
"beforeDevCommand": "", "beforeDevCommand": "",
"beforeBuildCommand": "" "beforeBuildCommand": ""
}, },
@ -32,4 +34,4 @@
"../../../../../examples/.icons/icon.ico" "../../../../../examples/.icons/icon.ico"
] ]
} }
} }

View File

@ -2,7 +2,9 @@
"$schema": "../../../../../../../../core/tauri-config-schema/schema.json", "$schema": "../../../../../../../../core/tauri-config-schema/schema.json",
"identifier": "fixture.app", "identifier": "fixture.app",
"build": { "build": {
"frontendDist": "../dist" "prodFrontend": {
"dist": "../dist"
},
}, },
"app": { "app": {
"withGlobalTauri": true, "withGlobalTauri": true,
@ -22,4 +24,4 @@
"icons/icon.ico" "icons/icon.ico"
] ]
} }
} }

View File

@ -1,7 +1,7 @@
{ {
"$schema": "http://json-schema.org/draft-07/schema#", "$schema": "http://json-schema.org/draft-07/schema#",
"title": "Config", "title": "Config",
"description": "The Tauri configuration object. It is read from a file where you can define your frontend assets, configure the bundler and define a tray icon.\n\nThe configuration file is generated by the [`tauri init`](https://tauri.app/v1/api/cli#init) command that lives in your Tauri application source directory (src-tauri).\n\nOnce generated, you may modify it at will to customize your Tauri application.\n\n## File Formats\n\nBy default, the configuration is defined as a JSON file named `tauri.conf.json`.\n\nTauri also supports JSON5 and TOML files via the `config-json5` and `config-toml` Cargo features, respectively. The JSON5 file name must be either `tauri.conf.json` or `tauri.conf.json5`. The TOML file name is `Tauri.toml`.\n\n## Platform-Specific Configuration\n\nIn addition to the default configuration file, Tauri can read a platform-specific configuration from `tauri.linux.conf.json`, `tauri.windows.conf.json`, `tauri.macos.conf.json`, `tauri.android.conf.json` and `tauri.ios.conf.json` (or `Tauri.linux.toml`, `Tauri.windows.toml`, `Tauri.macos.toml`, `Tauri.android.toml` and `Tauri.ios.toml` if the `Tauri.toml` format is used), which gets merged with the main configuration object.\n\n## Configuration Structure\n\nThe configuration is composed of the following objects:\n\n- [`package`](#packageconfig): Package settings - [`app`](#appconfig): The Tauri config - [`build`](#buildconfig): The build configuration - [`plugins`](#pluginconfig): The plugins config\n\n```json title=\"Example tauri.config.json file\" { \"productName\": \"tauri-app\", \"version\": \"0.1.0\" \"build\": { \"beforeBuildCommand\": \"\", \"beforeDevCommand\": \"\", \"devUrl\": \"../dist\", \"frontendDist\": \"../dist\" }, \"app\": { \"security\": { \"csp\": null }, \"windows\": [ { \"fullscreen\": false, \"height\": 600, \"resizable\": true, \"title\": \"Tauri App\", \"width\": 800 } ] }, \"bundle\": {} } ```", "description": "The Tauri configuration object. It is read from a file where you can define your frontend assets, configure the bundler and define a tray icon.\n\nThe configuration file is generated by the [`tauri init`](https://tauri.app/v1/api/cli#init) command that lives in your Tauri application source directory (src-tauri).\n\nOnce generated, you may modify it at will to customize your Tauri application.\n\n## File Formats\n\nBy default, the configuration is defined as a JSON file named `tauri.conf.json`.\n\nTauri also supports JSON5 and TOML files via the `config-json5` and `config-toml` Cargo features, respectively. The JSON5 file name must be either `tauri.conf.json` or `tauri.conf.json5`. The TOML file name is `Tauri.toml`.\n\n## Platform-Specific Configuration\n\nIn addition to the default configuration file, Tauri can read a platform-specific configuration from `tauri.linux.conf.json`, `tauri.windows.conf.json`, `tauri.macos.conf.json`, `tauri.android.conf.json` and `tauri.ios.conf.json` (or `Tauri.linux.toml`, `Tauri.windows.toml`, `Tauri.macos.toml`, `Tauri.android.toml` and `Tauri.ios.toml` if the `Tauri.toml` format is used), which gets merged with the main configuration object.\n\n## Configuration Structure\n\nThe configuration is composed of the following objects:\n\n- [`package`](#packageconfig): Package settings - [`app`](#appconfig): The Tauri config - [`build`](#buildconfig): The build configuration - [`plugins`](#pluginconfig): The plugins config\n\n```json title=\"Example tauri.config.json file\" { \"productName\": \"tauri-app\", \"version\": \"0.1.0\" \"build\": { \"beforeBuildCommand\": \"\", \"beforeDevCommand\": \"\", \"devUrl\": \"../dist\", \"prodFrontend\": { \"dist\": \"../dist\" }, }, \"app\": { \"security\": { \"csp\": null }, \"windows\": [ { \"fullscreen\": false, \"height\": 600, \"resizable\": true, \"title\": \"Tauri App\", \"width\": 800 } ] }, \"bundle\": {} } ```",
"type": "object", "type": "object",
"properties": { "properties": {
"$schema": { "$schema": {
@ -1097,18 +1097,18 @@
] ]
}, },
"devUrl": { "devUrl": {
"description": "The URL to load in development.\n\nThis is usually an URL to a dev server, which serves your application assets with hot-reload and HMR. Most modern JavaScript bundlers like [vite](https://vitejs.dev/guide/) provides a way to start a dev server by default.\n\nIf you don't have a dev server or don't want to use one, ignore this option and use [`frontendDist`](BuildConfig::frontend_dist) and point to a web assets directory, and Tauri CLI will run its built-in dev server and provide a simple hot-reload experience.", "description": "The URL to load in development.\n\nThis is usually an URL to a dev server, which serves your application assets with hot-reload and HMR. Most modern JavaScript bundlers like [vite](https://vitejs.dev/guide/) provides a way to start a dev server by default.\n\nIf you don't have a dev server or don't want to use one, ignore this option and use [`prodFrontend`](BuildConfig::prod_frontend) and point to a web assets directory, and Tauri CLI will run its built-in dev server and provide a simple hot-reload experience.",
"type": [ "type": [
"string", "string",
"null" "null"
], ],
"format": "uri" "format": "uri"
}, },
"frontendDist": { "prodFrontend": {
"description": "The path to the application assets (usually the `dist` folder of your javascript bundler) or a URL that could be either a custom protocol registered in the tauri app (for example: `myprotocol://`) or a remote URL (for example: `https://site.com/app`).\n\nWhen a path relative to the configuration file is provided, it is read recursively and all files are embedded in the application binary. Tauri then looks for an `index.html` and serves it as the default entry point for your application.\n\nYou can also provide a list of paths to be embedded, which allows granular control over what files are added to the binary. In this case, all files are added to the root and you must reference it that way in your HTML files.\n\nWhen a URL is provided, the application won't have bundled assets and the application will load that URL by default.", "description": "The path to the application assets (usually the `dist` folder of your javascript bundler) or a URL that could be either a custom protocol registered in the tauri app (for example: `myprotocol://`) or a remote URL (for example: `https://site.com/app`).\n\nWhen a path relative to the configuration file is provided, it is read recursively and all files are embedded in the application binary. Tauri then looks for an `index.html` and serves it as the default entry point for your application.\n\nYou can also provide a list of paths to be embedded, which allows granular control over what files are added to the binary. In this case, all files are added to the root and you must reference it that way in your HTML files.\n\nWhen a URL is provided, the application won't have bundled assets and the application will load that URL by default.",
"anyOf": [ "anyOf": [
{ {
"$ref": "#/definitions/AppUrl" "$ref": "#/definitions/ProdFrontend"
}, },
{ {
"type": "null" "type": "null"
@ -1161,23 +1161,51 @@
}, },
"additionalProperties": false "additionalProperties": false
}, },
"AppUrl": { "ProdFrontend": {
"description": "Defines the URL or assets to embed in the application.", "description": "Defines the URL or assets to embed in the application.",
"anyOf": [ "oneOf": [
{ {
"description": "The app's external URL, or the path to the directory containing the app assets.", "description": "An external URL to load.",
"allOf": [ "type": "object",
{ "required": [
"$ref": "#/definitions/WebviewUrl" "url"
],
"properties": {
"url": {
"type": "string",
"format": "uri"
} }
] },
"additionalProperties": false
},
{
"description": "Path to the folder containing the frontend dist assets.",
"type": "object",
"required": [
"dist"
],
"properties": {
"dist": {
"type": "string"
}
},
"additionalProperties": false
}, },
{ {
"description": "An array of files to embed on the app.", "description": "An array of files to embed on the app.",
"type": "array", "type": "object",
"items": { "required": [
"type": "string" "files"
} ],
"properties": {
"files": {
"type": "array",
"items": {
"type": "string"
}
}
},
"additionalProperties": false
} }
] ]
}, },

View File

@ -6,7 +6,7 @@ use crate::{
helpers::{ helpers::{
app_paths::{app_dir, tauri_dir}, app_paths::{app_dir, tauri_dir},
command_env, command_env,
config::{get as get_config, AppUrl, HookCommand, WebviewUrl, MERGE_CONFIG_EXTENSION_NAME}, config::{get as get_config, HookCommand, ProdFrontend, MERGE_CONFIG_EXTENSION_NAME},
resolve_merge_config, resolve_merge_config,
updater_signature::{secret_key as updater_secret_key, sign_file}, updater_signature::{secret_key as updater_secret_key, sign_file},
}, },
@ -29,7 +29,7 @@ use tauri_utils::platform::Target;
#[derive(Debug, Clone, Parser)] #[derive(Debug, Clone, Parser)]
#[clap( #[clap(
about = "Build your app in release mode and generate bundles and installers", about = "Build your app in release mode and generate bundles and installers",
long_about = "Build your app in release mode and generate bundles and installers. It makes use of the `build.frontendDist` property from your `tauri.conf.json` file. It also runs your `build.beforeBuildCommand` which usually builds your frontend into `build.frontendDist`. This will also run `build.beforeBundleCommand` before generating the bundles and installers of your app." long_about = "Build your app in release mode and generate bundles and installers. It makes use of the `build.prodFrontend` property from your `tauri.conf.json` file. It also runs your `build.beforeBuildCommand` which usually builds your frontend into `build.prodFrontend`. This will also run `build.beforeBundleCommand` before generating the bundles and installers of your app."
)] )]
pub struct Options { pub struct Options {
/// Binary to use to build the application, defaults to `cargo` /// Binary to use to build the application, defaults to `cargo`
@ -307,16 +307,16 @@ pub fn setup(target: Target, options: &mut Options, mobile: bool) -> Result<AppI
)?; )?;
} }
if let Some(AppUrl::Url(WebviewUrl::App(web_asset_path))) = &config_.build.frontend_dist { if let Some(ProdFrontend::Dist(web_asset_path)) = &config_.build.prod_frontend {
if !web_asset_path.exists() { if !web_asset_path.exists() {
return Err(anyhow::anyhow!( return Err(anyhow::anyhow!(
"Unable to find your web assets, did you forget to build your web app? Your frontendDist is set to \"{:?}\".", "Unable to find your web assets, did you forget to build your web app? Your prodFrontend is set to \"{:?}\".",
web_asset_path web_asset_path
)); ));
} }
if web_asset_path.canonicalize()?.file_name() == Some(std::ffi::OsStr::new("src-tauri")) { if web_asset_path.canonicalize()?.file_name() == Some(std::ffi::OsStr::new("src-tauri")) {
return Err(anyhow::anyhow!( return Err(anyhow::anyhow!(
"The configured frontendDist is the `src-tauri` folder. Please isolate your web assets on a separate folder and update `tauri.conf.json > build > frontendDist`.", "The configured prodFrontend is the `src-tauri` folder. Please isolate your web assets on a separate folder and update `tauri.conf.json > build > prodFrontend`.",
)); ));
} }
@ -328,7 +328,7 @@ pub fn setup(target: Target, options: &mut Options, mobile: bool) -> Result<AppI
} }
if !out_folders.is_empty() { if !out_folders.is_empty() {
return Err(anyhow::anyhow!( return Err(anyhow::anyhow!(
"The configured frontendDist includes the `{:?}` {}. Please isolate your web assets on a separate folder and update `tauri.conf.json > build > frontendDist`.", "The configured prodFrontend includes the `{:?}` {}. Please isolate your web assets on a separate folder and update `tauri.conf.json > build > prodFrontend`.",
out_folders, out_folders,
if out_folders.len() == 1 { "folder" }else { "folders" } if out_folders.len() == 1 { "folder" }else { "folders" }
) )

View File

@ -6,7 +6,7 @@ use crate::{
helpers::{ helpers::{
app_paths::{app_dir, tauri_dir}, app_paths::{app_dir, tauri_dir},
command_env, command_env,
config::{get as get_config, reload as reload_config, AppUrl, BeforeDevCommand, WebviewUrl}, config::{get as get_config, reload as reload_config, BeforeDevCommand, ProdFrontend},
resolve_merge_config, resolve_merge_config,
}, },
interface::{AppInterface, DevProcess, ExitReason, Interface}, interface::{AppInterface, DevProcess, ExitReason, Interface},
@ -313,16 +313,16 @@ pub fn setup(target: Target, options: &mut Options, mobile: bool) -> Result<AppI
.build .build
.dev_url .dev_url
.clone(); .clone();
let frontend_dist = config let prod_frontend = config
.lock() .lock()
.unwrap() .unwrap()
.as_ref() .as_ref()
.unwrap() .unwrap()
.build .build
.frontend_dist .prod_frontend
.clone(); .clone();
if !options.no_dev_server && dev_url.is_none() { if !options.no_dev_server && dev_url.is_none() {
if let Some(AppUrl::Url(WebviewUrl::App(path))) = &frontend_dist { if let Some(ProdFrontend::Dist(path)) = &prod_frontend {
use crate::helpers::web_dev_server; use crate::helpers::web_dev_server;
if path.exists() { if path.exists() {
let path = path.canonicalize()?; let path = path.canonicalize()?;

View File

@ -39,7 +39,7 @@ impl Framework {
.into() .into()
} }
pub fn frontend_dist(&self) -> String { pub fn prod_frontend(&self) -> String {
match self { match self {
Self::SolidJS => "../dist", Self::SolidJS => "../dist",
Self::SolidStart => "../dist/public", Self::SolidStart => "../dist/public",

View File

@ -33,8 +33,8 @@ pub fn items(app_dir: Option<&PathBuf>, tauri_dir: Option<&Path>) -> Vec<Section
.unwrap_or_else(|| "unset".to_string()); .unwrap_or_else(|| "unset".to_string());
items.push(SectionItem::new().description(format!("CSP: {csp}"))); items.push(SectionItem::new().description(format!("CSP: {csp}")));
if let Some(frontend_dist) = &config.build.frontend_dist { if let Some(prod_frontend) = &config.build.prod_frontend {
items.push(SectionItem::new().description(format!("frontendDist: {frontend_dist}"))); items.push(SectionItem::new().description(format!("prodFrontend: {prod_frontend}")));
} }
if let Some(dev_url) = &config.build.dev_url { if let Some(dev_url) = &config.build.dev_url {

View File

@ -56,7 +56,7 @@ pub struct Options {
window_title: Option<String>, window_title: Option<String>,
/// Web assets location, relative to <project-dir>/src-tauri /// Web assets location, relative to <project-dir>/src-tauri
#[clap(short = 'D', long)] #[clap(short = 'D', long)]
frontend_dist: Option<String>, prod_frontend: Option<String>,
/// Url of your dev server /// Url of your dev server
#[clap(short = 'P', long)] #[clap(short = 'P', long)]
dev_url: Option<String>, dev_url: Option<String>,
@ -109,9 +109,9 @@ impl Options {
) )
})?; })?;
self.frontend_dist = self.frontend_dist.map(|s| Ok(Some(s))).unwrap_or_else(|| request_input( self.prod_frontend = self.prod_frontend.map(|s| Ok(Some(s))).unwrap_or_else(|| request_input(
r#"Where are your web assets (HTML/CSS/JS) located, relative to the "<current dir>/src-tauri/tauri.conf.json" file that will be created?"#, r#"Where are your web assets (HTML/CSS/JS) located, relative to the "<current dir>/src-tauri/tauri.conf.json" file that will be created?"#,
init_defaults.framework.as_ref().map(|f| f.frontend_dist()), init_defaults.framework.as_ref().map(|f| f.prod_frontend()),
self.ci, self.ci,
false, false,
))?; ))?;
@ -190,10 +190,10 @@ pub fn command(mut options: Options) -> Result<()> {
data.insert("tauri_dep", to_json(tauri_dep)); data.insert("tauri_dep", to_json(tauri_dep));
data.insert("tauri_build_dep", to_json(tauri_build_dep)); data.insert("tauri_build_dep", to_json(tauri_build_dep));
data.insert( data.insert(
"frontend_dist", "prod_frontend",
to_json( to_json(
options options
.frontend_dist .prod_frontend
.unwrap_or_else(|| "../dist".to_string()), .unwrap_or_else(|| "../dist".to_string()),
), ),
); );

View File

@ -174,7 +174,23 @@ fn process_package_metadata(config: &mut Map<String, Value>) {
fn process_build(config: &mut Map<String, Value>) { fn process_build(config: &mut Map<String, Value>) {
if let Some(build_config) = config.get_mut("build").and_then(|b| b.as_object_mut()) { if let Some(build_config) = config.get_mut("build").and_then(|b| b.as_object_mut()) {
if let Some(dist_dir) = build_config.remove("distDir") { if let Some(dist_dir) = build_config.remove("distDir") {
build_config.insert("frontendDist".into(), dist_dir); match &dist_dir {
Value::Array(_files) => {
let mut frontend = Map::new();
frontend.insert("files".to_string(), dist_dir);
build_config.insert("prodFrontend".into(), frontend.into());
}
Value::String(url_or_path) => {
let mut frontend = Map::new();
if url::Url::parse(url_or_path).is_ok() {
frontend.insert("url".to_string(), dist_dir);
} else {
frontend.insert("dist".to_string(), dist_dir);
}
build_config.insert("prodFrontend".into(), frontend.into());
}
_ => (),
}
} }
if let Some(dist_dir) = build_config.remove("devPath") { if let Some(dist_dir) = build_config.remove("devPath") {
build_config.insert("devUrl".into(), dist_dir); build_config.insert("devUrl".into(), dist_dir);
@ -701,7 +717,7 @@ mod test {
// build object // build object
assert_eq!( assert_eq!(
migrated["build"]["frontendDist"], migrated["build"]["prodFrontend"]["dist"],
original["build"]["distDir"] original["build"]["distDir"]
); );
assert_eq!(migrated["build"]["devUrl"], original["build"]["devPath"]); assert_eq!(migrated["build"]["devUrl"], original["build"]["devPath"]);

View File

@ -31,7 +31,7 @@ use std::env::{set_current_dir, set_var};
#[derive(Debug, Clone, Parser)] #[derive(Debug, Clone, Parser)]
#[clap( #[clap(
about = "Build your app in release mode for Android and generate APKs and AABs", about = "Build your app in release mode for Android and generate APKs and AABs",
long_about = "Build your app in release mode for Android and generate APKs and AABs. It makes use of the `build.frontendDist` property from your `tauri.conf.json` file. It also runs your `build.beforeBuildCommand` which usually builds your frontend into `build.frontendDist`." long_about = "Build your app in release mode for Android and generate APKs and AABs. It makes use of the `build.prodFrontend` property from your `tauri.conf.json` file. It also runs your `build.beforeBuildCommand` which usually builds your frontend into `build.prodFrontend`."
)] )]
pub struct Options { pub struct Options {
/// Builds with the debug flag /// Builds with the debug flag

View File

@ -32,7 +32,7 @@ use std::{env::set_current_dir, fs};
#[derive(Debug, Clone, Parser)] #[derive(Debug, Clone, Parser)]
#[clap( #[clap(
about = "Build your app in release mode for iOS and generate IPAs", about = "Build your app in release mode for iOS and generate IPAs",
long_about = "Build your app in release mode for iOS and generate IPAs. It makes use of the `build.frontendDist` property from your `tauri.conf.json` file. It also runs your `build.beforeBuildCommand` which usually builds your frontend into `build.frontendDist`." long_about = "Build your app in release mode for iOS and generate IPAs. It makes use of the `build.prodFrontend` property from your `tauri.conf.json` file. It also runs your `build.beforeBuildCommand` which usually builds your frontend into `build.prodFrontend`."
)] )]
pub struct Options { pub struct Options {
/// Builds with the debug flag /// Builds with the debug flag

View File

@ -6,7 +6,9 @@
"beforeDevCommand": "yarn dev", "beforeDevCommand": "yarn dev",
"beforeBuildCommand": "yarn build", "beforeBuildCommand": "yarn build",
"devUrl": "http://localhost:1420", "devUrl": "http://localhost:1420",
"frontendDist": "../dist" "prodFrontend": {
"dist": "../dist"
},
}, },
"app": { "app": {
"withGlobalTauri": false, "withGlobalTauri": false,
@ -34,4 +36,4 @@
"icons/icon.ico" "icons/icon.ico"
] ]
} }
} }

View File

@ -3,7 +3,9 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.{{ plugin_name }}", "identifier": "com.tauri.{{ plugin_name }}",
"build": { "build": {
"frontendDist": "../public" "prodFrontend": {
"dist": "../public"
},
}, },
"app": { "app": {
"windows": [ "windows": [
@ -30,4 +32,4 @@
"icons/icon.ico" "icons/icon.ico"
] ]
} }
} }

View File

@ -3,7 +3,9 @@
"version": "0.1.0", "version": "0.1.0",
"identifier": "com.tauri.dev", "identifier": "com.tauri.dev",
"build": { "build": {
"frontendDist": "{{ frontend_dist }}", "prodFrontend": {
"dist": "{{ prod_frontend }}"
},
"devUrl": "{{ dev_url }}", "devUrl": "{{ dev_url }}",
"beforeDevCommand": "{{ before_dev_command }}", "beforeDevCommand": "{{ before_dev_command }}",
"beforeBuildCommand": "{{ before_build_command }}" "beforeBuildCommand": "{{ before_build_command }}"
@ -33,4 +35,4 @@
"icons/icon.ico" "icons/icon.ico"
] ]
} }
} }