diff --git a/frontend/src/metabase-lib/lib/metadata/Database.ts b/frontend/src/metabase-lib/lib/metadata/Database.ts index 68633e3e81d2378210a33634b8e1cd9a33d3beed..90248dc2bbef04de881eb81238bf849cb6f9e0c1 100644 --- a/frontend/src/metabase-lib/lib/metadata/Database.ts +++ b/frontend/src/metabase-lib/lib/metadata/Database.ts @@ -96,6 +96,10 @@ export default class Database extends Base { return this.hasFeature("expressions") && this.hasFeature("left-join"); } + canWrite() { + return this.native_permissions === "write"; + } + // QUESTIONS newQuestion() { return this.question() diff --git a/frontend/src/metabase-lib/lib/metadata/Database.unit.spec.ts b/frontend/src/metabase-lib/lib/metadata/Database.unit.spec.ts index fa3b6b55ebc01832448ba140e267b1e453fe22c6..9c1b257cdb452cca0033d06dd44fbd39220d9d83 100644 --- a/frontend/src/metabase-lib/lib/metadata/Database.unit.spec.ts +++ b/frontend/src/metabase-lib/lib/metadata/Database.unit.spec.ts @@ -260,4 +260,24 @@ describe("Database", () => { expect(database1.savedQuestionsDatabase()).toBe(database2); }); }); + + describe("canWrite", () => { + it("should be true for a db with write permissions", () => { + const database = new Database({ + id: 1, + native_permissions: "write", + }); + + expect(database.canWrite()).toBe(true); + }); + + it("should be false for a db without write permissions", () => { + const database = new Database({ + id: 1, + native_permissions: "none", + }); + + expect(database.canWrite()).toBe(false); + }); + }); }); diff --git a/frontend/src/metabase/nav/containers/Navbar.jsx b/frontend/src/metabase/nav/containers/Navbar.jsx index 6c810fb5137783bf16d8aa62f2aeea399df03ccc..f7f5f654599cb74a6ce21354644b8d8727918f44 100644 --- a/frontend/src/metabase/nav/containers/Navbar.jsx +++ b/frontend/src/metabase/nav/containers/Navbar.jsx @@ -28,6 +28,7 @@ import { getHasDataAccess, getHasNativeWrite, getPlainNativeQuery, + getHasDbWithJsonEngine, } from "metabase/new_query/selectors"; import Database from "metabase/entities/databases"; @@ -38,6 +39,7 @@ const mapStateToProps = (state, props) => ({ plainNativeQuery: getPlainNativeQuery(state), hasDataAccess: getHasDataAccess(state), hasNativeWrite: getHasNativeWrite(state), + hasDbWithJsonEngine: getHasDbWithJsonEngine(state, props), }); import { getDefaultSearchColor } from "metabase/nav/constants"; @@ -114,7 +116,7 @@ export default class Navbar extends Component { } renderMainNav() { - const { hasDataAccess, hasNativeWrite } = this.props; + const { hasDataAccess, hasNativeWrite, hasDbWithJsonEngine } = this.props; return ( <NavRoot @@ -178,7 +180,9 @@ export default class Navbar extends Component { ...(hasNativeWrite ? [ { - title: t`SQL query`, + title: hasDbWithJsonEngine + ? t`Native query` + : t`SQL query`, icon: `sql`, link: Urls.newQuestion({ type: "native", diff --git a/frontend/src/metabase/new_query/selectors.js b/frontend/src/metabase/new_query/selectors.js index d0590a532688efd02c44c7a20d622ac2788a7bf4..8f2f19d3c2adf3737df277ed69de8bba6d01ba6e 100644 --- a/frontend/src/metabase/new_query/selectors.js +++ b/frontend/src/metabase/new_query/selectors.js @@ -4,9 +4,11 @@ */ import { createSelector } from "reselect"; + import { getMetadata, getDatabases } from "metabase/selectors/metadata"; import NativeQuery from "metabase-lib/lib/queries/NativeQuery"; import Question from "metabase-lib/lib/Question"; +import { getEngineNativeType } from "metabase/lib/engine"; export const getPlainNativeQuery = state => { const metadata = getMetadata(state); @@ -37,3 +39,10 @@ export const getHasNativeWrite = createSelector( (databaseMap = {}) => Object.values(databaseMap).some(d => d.native_permissions === "write"), ); + +export const getHasDbWithJsonEngine = (state, props) => { + return (props.databases || []).some(database => { + const isJsonEngine = getEngineNativeType(database.engine) === "json"; + return database.canWrite() && isJsonEngine; + }); +}; diff --git a/frontend/test/metabase/scenarios/native/native-mongo.cy.spec.js b/frontend/test/metabase/scenarios/native/native-mongo.cy.spec.js index 07b0c81a78712533cb72f990efdfa5cf1125f261..2783c2be0bbfb1c782c91ce8f8dcd979a81b27a6 100644 --- a/frontend/test/metabase/scenarios/native/native-mongo.cy.spec.js +++ b/frontend/test/metabase/scenarios/native/native-mongo.cy.spec.js @@ -2,14 +2,16 @@ import { restore, modal } from "__support__/e2e/cypress"; const MONGO_DB_NAME = "QA Mongo4"; -describe("scenatios > question > native > mongo", () => { +describe("scenarios > question > native > mongo", () => { before(() => { cy.intercept("POST", "/api/card").as("createQuestion"); restore("mongo-4"); cy.signInAsNormalUser(); - cy.visit("/question/new"); + cy.visit("/"); + cy.findByText("New").click(); + // Reproduces metabase#20499 issue cy.findByText("Native query").click(); cy.findByText(MONGO_DB_NAME).click();