Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion app/client/public/404.html
Original file line number Diff line number Diff line change
@@ -1,8 +1,9 @@
<!DOCTYPE html>
<html lang="en">
<html lang="en" translate="no">

<head>
<meta charset="utf-8" />
<meta name="google" content="notranslate" />
<link rel="shortcut icon"
href="https://res.cloudinary.com/dwpfockn8/image/upload/v1597920848/favicons/favicon-orange_pxfmdc.ico" />
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no" />
Expand Down
5 changes: 4 additions & 1 deletion app/client/public/index.html
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
<!DOCTYPE html>
<html lang="en">
<html lang='{{env "APPSMITH_DEFAULT_HTML_LANG"}}' translate="no">
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The template has no inline fallback value. The caddy-reconfigure.mjs provides the "en" default only during Docker deployment. Tagging @ashit-rath to validate if this concern is not valid.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's add an inline fallback value if we can. Better to be safe if the option is available

<head>
<meta charset="utf-8" />
<meta name="google" content="notranslate" />
<meta
name="viewport"
content="width=device-width, initial-scale=1, shrink-to-fit=no, maximum-scale=1"
Expand Down Expand Up @@ -267,6 +268,8 @@
disableIframeWidgetSandbox: parseConfig(
'{{env "APPSMITH_DISABLE_IFRAME_WIDGET_SANDBOX"}}',
),
defaultHtmlLang:
parseConfig('{{env "APPSMITH_DEFAULT_HTML_LANG"}}') || "",
customerPortalUrl:
parseConfig('{{env "APPSMITH_CUSTOMER_PORTAL_URL"}}') ||
"https://customer.appsmith.com",
Expand Down
1 change: 1 addition & 0 deletions app/client/src/ce/api/ApplicationApi.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,7 @@ export interface UpdateApplicationPayload {
navigationSetting?: NavigationSetting;
themeSetting?: ThemeSetting;
appPositioning?: LayoutSystemTypeConfig;
htmlLang?: string;
};
forkingEnabled?: boolean;
}
Expand Down
6 changes: 6 additions & 0 deletions app/client/src/ce/configs/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ export interface INJECTED_CONFIGS {
googleRecaptchaSiteKey: string;
supportEmail: string;
disableIframeWidgetSandbox: boolean;
defaultHtmlLang: string;
pricingUrl: string;
customerPortalUrl: string;
}
Expand Down Expand Up @@ -111,6 +112,7 @@ export const getConfigsFromEnvVars = (): INJECTED_CONFIGS => {
.APPSMITH_DISABLE_IFRAME_WIDGET_SANDBOX
? process.env.APPSMITH_DISABLE_IFRAME_WIDGET_SANDBOX.length > 0
: false,
defaultHtmlLang: process.env.APPSMITH_DEFAULT_HTML_LANG || "",
pricingUrl: process.env.REACT_APP_PRICING_URL || "",
customerPortalUrl: process.env.REACT_APP_CUSTOMER_PORTAL_URL || "",
};
Expand Down Expand Up @@ -255,6 +257,10 @@ export const getAppsmithConfigs = (): AppsmithUIConfigs => {
ENV_CONFIG.disableIframeWidgetSandbox ||
APPSMITH_FEATURE_CONFIGS?.disableIframeWidgetSandbox ||
false,
defaultHtmlLang:
ENV_CONFIG.defaultHtmlLang ||
APPSMITH_FEATURE_CONFIGS?.defaultHtmlLang ||
"",
pricingUrl:
ENV_CONFIG.pricingUrl || APPSMITH_FEATURE_CONFIGS?.pricingUrl || "",
customerPortalUrl:
Expand Down
1 change: 1 addition & 0 deletions app/client/src/ce/configs/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ export interface AppsmithUIConfigs {
};
appsmithSupportEmail: string;
disableIframeWidgetSandbox: boolean;
defaultHtmlLang: string;
pricingUrl: string;
customerPortalUrl: string;
}
Expand Down
3 changes: 3 additions & 0 deletions app/client/src/ce/constants/messages.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1962,6 +1962,9 @@ export const GENERAL_SETTINGS_NAME_EMPTY_MESSAGE = () =>
export const GENERAL_SETTINGS_NAME_SPECIAL_CHARACTER_ERROR = () =>
"Only alphanumeric or '-()' are allowed";
export const GENERAL_SETTINGS_APP_ICON_LABEL = () => "App icon";
export const GENERAL_SETTINGS_APP_LANGUAGE_LABEL = () => "HTML language";
export const GENERAL_SETTINGS_APP_LANGUAGE_TOOLTIP = () =>
"Sets the lang attribute on the published app. This tells browsers what language your content is in and prevents unwanted auto-translation. Use a BCP 47 code (e.g. en, de, fr, ja).";
export const GENERAL_SETTINGS_APP_URL_LABEL = () => "App slug";
export const GENERAL_SETTINGS_APP_URL_PLACEHOLDER = () => "app-url";
export const GENERAL_SETTINGS_APP_URL_PLACEHOLDER_FETCHING = () =>
Expand Down
1 change: 1 addition & 0 deletions app/client/src/entities/Application/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ export interface ApplicationPayload {
appPositioning?: LayoutSystemTypeConfig;
navigationSetting?: NavigationSetting;
themeSetting?: ThemeSetting;
htmlLang?: string;
};
collapseInvisibleWidgets?: boolean;
evaluationVersion?: EvaluationVersion;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -206,7 +206,7 @@ function AppSettings() {
DIVIDER_AND_SPACING_HEIGHT;

return (
<Wrapper className="flex flex-row">
<Wrapper className="flex flex-row" translate="no">
<div className="w-1/2">
{SectionHeadersConfig.map((config) => (
<SectionHeader key={config.name} {...config} />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@ import {
import type { UpdateApplicationPayload } from "ee/api/ApplicationApi";
import {
GENERAL_SETTINGS_APP_ICON_LABEL,
GENERAL_SETTINGS_APP_LANGUAGE_LABEL,
GENERAL_SETTINGS_APP_LANGUAGE_TOOLTIP,
GENERAL_SETTINGS_APP_NAME_LABEL,
GENERAL_SETTINGS_NAME_EMPTY_MESSAGE,
GENERAL_SETTINGS_APP_URL_LABEL,
Expand Down Expand Up @@ -38,8 +40,7 @@ import {
Tooltip,
} from "@appsmith/ads";
import { IconSelector } from "@appsmith/ads-old";
import React, { useCallback, useMemo, useState } from "react";
import { useEffect } from "react";
import React, { useCallback, useEffect, useMemo, useState } from "react";
import StaticURLConfirmationModal from "./StaticURLConfirmationModal";
import { debounce } from "lodash";
import { useDispatch, useSelector } from "react-redux";
Expand Down Expand Up @@ -116,6 +117,9 @@ function GeneralSettings() {
const [applicationIcon, setApplicationIcon] = useState(
application?.icon as AppIconName,
);
const [htmlLang, setHtmlLang] = useState(
application?.applicationDetail?.htmlLang || "",
);
const [applicationSlug, setApplicationSlug] = useState(
application?.staticUrlSettings?.uniqueSlug || "",
);
Expand All @@ -138,6 +142,30 @@ function GeneralSettings() {
[application, application?.name, isSavingAppName],
);

useEffect(
function syncHtmlLang() {
setHtmlLang(application?.applicationDetail?.htmlLang || "");
},
[application?.applicationDetail?.htmlLang],
);

const saveHtmlLang = useCallback(
(value: string) => {
const trimmed = value.trim().toLowerCase();
const current = application?.applicationDetail?.htmlLang || "";

if (trimmed === current) return;

dispatch(
updateApplication(applicationId, {
currentApp: true,
applicationDetail: { htmlLang: trimmed },
}),
);
},
[applicationId, application?.applicationDetail?.htmlLang, dispatch],
);

useEffect(
function updateApplicationSlug() {
setApplicationSlug(application?.staticUrlSettings?.uniqueSlug || "");
Expand Down Expand Up @@ -467,6 +495,27 @@ function GeneralSettings() {
/>
</IconSelectorWrapper>

<div className="pt-2 pb-2">
<Input
id="t--general-settings-app-language"
label={createMessage(GENERAL_SETTINGS_APP_LANGUAGE_LABEL)}
onBlur={() => saveHtmlLang(htmlLang)}
onChange={(value: string) => setHtmlLang(value)}
onKeyPress={(ev: React.KeyboardEvent) => {
if (ev.key === "Enter") {
saveHtmlLang(htmlLang);
}
}}
placeholder="en"
size="md"
type="text"
value={htmlLang}
/>
<Text className="mt-1" kind="body-s">
{createMessage(GENERAL_SETTINGS_APP_LANGUAGE_TOOLTIP)}
</Text>
</div>

{isStaticUrlFeatureEnabled && (
<div className="flex content-center justify-between pt-2">
<Switch
Expand Down
9 changes: 6 additions & 3 deletions app/client/src/pages/AppViewer/AppViewerHtmlTitle.tsx
Original file line number Diff line number Diff line change
@@ -1,19 +1,22 @@
import React from "react";
import { Helmet } from "react-helmet";
import { getAppsmithConfigs } from "ee/configs";

interface Props {
name?: string;
description?: string;
lang?: string;
}

const { defaultHtmlLang } = getAppsmithConfigs();

function AppViewerHtmlTitle(props: Props) {
const { description, name } = props;
const { description, lang, name } = props;

// if no name is passed, just return null
if (!name) return null;

return (
<Helmet>
<Helmet htmlAttributes={{ lang: lang || defaultHtmlLang || "en" }}>
<title>{name}</title>
{description && <meta content={description} name="description" />}
</Helmet>
Expand Down
1 change: 1 addition & 0 deletions app/client/src/pages/AppViewer/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -263,6 +263,7 @@ function AppViewer(props: Props) {
)}
<HtmlTitle
description={pageDescription}
lang={currentApplicationDetails?.applicationDetail?.htmlLang}
name={currentApplicationDetails?.name}
/>
<AppViewerBodyContainer
Expand Down
6 changes: 5 additions & 1 deletion app/client/src/pages/Editor/PropertyPane/PropertyPaneTab.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,11 @@ export function PropertyPaneTab(props: PropertyPaneTabProps) {
);

return (
<StyledTabs onValueChange={onValueChange} value={tabs[selectedIndex]}>
<StyledTabs
onValueChange={onValueChange}
translate="no"
value={tabs[selectedIndex]}
>
<TabsList>
{props.contentComponent && <Tab value={tabs[0]}>Content</Tab>}
{props.styleComponent && <Tab value={tabs[1]}>Style</Tab>}
Expand Down
2 changes: 1 addition & 1 deletion app/client/src/widgets/CustomWidget/component/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -213,7 +213,7 @@ function CustomComponent(props: CustomComponentProps) {
]);

const srcDoc = `
<html>
<html translate="no">
<head>
<style>${css}</style>
</head>
Expand Down
2 changes: 1 addition & 1 deletion app/client/src/widgets/ExternalWidget/component/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,7 @@ function ExternalComponent(props: any) {
}, [props.width, props.height]);

const srcDoc = `
<html>
<html translate="no">
<head>
<script src="https://unpkg.com/@babel/standalone/babel.min.js"></script>
<style>${css}</style>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ interface CreateHtmlTemplateProps {
export const createHtmlTemplate = (props: CreateHtmlTemplateProps) => {
const { cssTokens, onConsole, srcDoc } = props;

return `<html>
return `<html translate="no">
<head>
<style>${css}</style>
<style data-appsmith-theme>${cssTokens}</style>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,9 @@ public class ApplicationDetailCE {
@JsonView({Views.Public.class, Git.class})
Application.ThemeSetting themeSetting;

@JsonView({Views.Public.class, Git.class})
String htmlLang;

public ApplicationDetailCE() {
this.appPositioning = null;
this.navigationSetting = null;
Expand Down
3 changes: 2 additions & 1 deletion deploy/docker/fs/opt/appsmith/caddy-reconfigure.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -229,7 +229,8 @@ function finalizeHtmlFiles() {
APPSMITH_VERSION_ID: info?.version ?? "",
APPSMITH_VERSION_SHA: info?.commitSha ?? "",
APPSMITH_VERSION_RELEASE_DATE: info?.imageBuiltAt ?? "",
APPSMITH_HOSTNAME: process.env.HOSTNAME ?? "appsmith-0"
APPSMITH_HOSTNAME: process.env.HOSTNAME ?? "appsmith-0",
APPSMITH_DEFAULT_HTML_LANG: process.env.APPSMITH_DEFAULT_HTML_LANG || "en",
}

for (const file of ["index.html", "404.html"]) {
Expand Down
3 changes: 2 additions & 1 deletion deploy/docker/fs/opt/appsmith/templates/loading.html
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
<!DOCTYPE html>
<html lang="en">
<html lang="en" translate="no">
<head>
<meta charset="utf-8" http-equiv="refresh" content="3"/>
<meta name="google" content="notranslate" />
<link
rel="shortcut icon"
href="https://assets.appsmith.com/appsmith-favicon-orange.ico"
Expand Down
Loading