diff --git a/datafusion/common/src/dfschema.rs b/datafusion/common/src/dfschema.rs
index f098f98a744c..8109c1c126b8 100644
--- a/datafusion/common/src/dfschema.rs
+++ b/datafusion/common/src/dfschema.rs
@@ -165,8 +165,8 @@ impl DFSchema {
     ///
     /// To create a schema from an Arrow schema without a qualifier, use
     /// `DFSchema::try_from`.
-    pub fn try_from_qualified_schema<'a>(
-        qualifier: impl Into<TableReference<'a>>,
+    pub fn try_from_qualified_schema(
+        qualifier: impl Into<TableReference>,
         schema: &Schema,
     ) -> Result<Self> {
         let qualifier = qualifier.into();
@@ -181,8 +181,8 @@ impl DFSchema {
     }
 
     /// Create a `DFSchema` from an Arrow schema where all the fields have a given qualifier
-    pub fn from_field_specific_qualified_schema<'a>(
-        qualifiers: Vec<Option<impl Into<TableReference<'a>>>>,
+    pub fn from_field_specific_qualified_schema(
+        qualifiers: Vec<Option<impl Into<TableReference>>>,
         schema: &SchemaRef,
     ) -> Result<Self> {
         let owned_qualifiers = qualifiers
diff --git a/datafusion/common/src/schema_reference.rs b/datafusion/common/src/schema_reference.rs
index a7dd49e5c33d..60e21f232e82 100644
--- a/datafusion/common/src/schema_reference.rs
+++ b/datafusion/common/src/schema_reference.rs
@@ -15,20 +15,15 @@
 // specific language governing permissions and limitations
 // under the License.
 
-use std::borrow::Cow;
+use std::sync::Arc;
 
 #[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
-pub enum SchemaReference<'a> {
-    Bare {
-        schema: Cow<'a, str>,
-    },
-    Full {
-        schema: Cow<'a, str>,
-        catalog: Cow<'a, str>,
-    },
+pub enum SchemaReference {
+    Bare { schema: Arc<str> },
+    Full { schema: Arc<str>, catalog: Arc<str> },
 }
 
-impl SchemaReference<'_> {
+impl SchemaReference {
     /// Get only the schema name that this references.
     pub fn schema_name(&self) -> &str {
         match self {
@@ -38,9 +33,9 @@ impl SchemaReference<'_> {
     }
 }
 
-pub type OwnedSchemaReference = SchemaReference<'static>;
+pub type OwnedSchemaReference = SchemaReference;
 
-impl std::fmt::Display for SchemaReference<'_> {
+impl std::fmt::Display for SchemaReference {
     fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
         match self {
             Self::Bare { schema } => write!(f, "{schema}"),
@@ -49,16 +44,8 @@ impl std::fmt::Display for SchemaReference<'_> {
     }
 }
 
-impl<'a> From<&'a OwnedSchemaReference> for SchemaReference<'a> {
+impl<'a> From<&'a OwnedSchemaReference> for SchemaReference {
     fn from(value: &'a OwnedSchemaReference) -> Self {
-        match value {
-            SchemaReference::Bare { schema } => SchemaReference::Bare {
-                schema: Cow::Borrowed(schema),
-            },
-            SchemaReference::Full { schema, catalog } => SchemaReference::Full {
-                schema: Cow::Borrowed(schema),
-                catalog: Cow::Borrowed(catalog),
-            },
-        }
+        value.clone()
     }
 }
diff --git a/datafusion/common/src/table_reference.rs b/datafusion/common/src/table_reference.rs
index 55681ece1016..1ffcbb8f34aa 100644
--- a/datafusion/common/src/table_reference.rs
+++ b/datafusion/common/src/table_reference.rs
@@ -16,20 +16,20 @@
 // under the License.
 
 use crate::utils::{parse_identifiers_normalized, quote_identifier};
-use std::borrow::Cow;
+use std::sync::Arc;
 
 /// A resolved path to a table of the form "catalog.schema.table"
 #[derive(Debug, Clone)]
-pub struct ResolvedTableReference<'a> {
+pub struct ResolvedTableReference {
     /// The catalog (aka database) containing the table
-    pub catalog: Cow<'a, str>,
+    pub catalog: Arc<str>,
     /// The schema containing the table
-    pub schema: Cow<'a, str>,
+    pub schema: Arc<str>,
     /// The table name
-    pub table: Cow<'a, str>,
+    pub table: Arc<str>,
 }
 
-impl<'a> std::fmt::Display for ResolvedTableReference<'a> {
+impl std::fmt::Display for ResolvedTableReference {
     fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
         write!(f, "{}.{}.{}", self.catalog, self.schema, self.table)
     }
@@ -68,27 +68,27 @@ impl<'a> std::fmt::Display for ResolvedTableReference<'a> {
 /// assert_eq!(table_reference, TableReference::partial("myschema", "mytable"));
 ///```
 #[derive(Debug, Clone, PartialEq, Eq, Hash, PartialOrd, Ord)]
-pub enum TableReference<'a> {
+pub enum TableReference {
     /// An unqualified table reference, e.g. "table"
     Bare {
         /// The table name
-        table: Cow<'a, str>,
+        table: Arc<str>,
     },
     /// A partially resolved table reference, e.g. "schema.table"
     Partial {
         /// The schema containing the table
-        schema: Cow<'a, str>,
+        schema: Arc<str>,
         /// The table name
-        table: Cow<'a, str>,
+        table: Arc<str>,
     },
     /// A fully resolved table reference, e.g. "catalog.schema.table"
     Full {
         /// The catalog (aka database) containing the table
-        catalog: Cow<'a, str>,
+        catalog: Arc<str>,
         /// The schema containing the table
-        schema: Cow<'a, str>,
+        schema: Arc<str>,
         /// The table name
-        table: Cow<'a, str>,
+        table: Arc<str>,
     },
 }
 
@@ -102,9 +102,9 @@ pub enum TableReference<'a> {
 /// let table_reference = TableReference::from("mytable");
 /// let owned_reference = table_reference.to_owned_reference();
 /// ```
-pub type OwnedTableReference = TableReference<'static>;
+pub type OwnedTableReference = TableReference;
 
-impl std::fmt::Display for TableReference<'_> {
+impl std::fmt::Display for TableReference {
     fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
         match self {
             TableReference::Bare { table } => write!(f, "{table}"),
@@ -120,9 +120,9 @@ impl std::fmt::Display for TableReference<'_> {
     }
 }
 
-impl<'a> TableReference<'a> {
+impl TableReference {
     /// Convenience method for creating a typed none `None`
-    pub fn none() -> Option<TableReference<'a>> {
+    pub fn none() -> Option<TableReference> {
         None
     }
 
@@ -131,7 +131,7 @@ impl<'a> TableReference<'a> {
     /// As described on [`TableReference`] this does *NO* parsing at
     /// all, so "Foo.Bar" stays as a reference to the table named
     /// "Foo.Bar" (rather than "foo"."bar")
-    pub fn bare(table: impl Into<Cow<'a, str>>) -> TableReference<'a> {
+    pub fn bare(table: &str) -> TableReference {
         TableReference::Bare {
             table: table.into(),
         }
@@ -140,10 +140,7 @@ impl<'a> TableReference<'a> {
     /// Convenience method for creating a [`TableReference::Partial`].
     ///
     /// As described on [`TableReference`] this does *NO* parsing at all.
-    pub fn partial(
-        schema: impl Into<Cow<'a, str>>,
-        table: impl Into<Cow<'a, str>>,
-    ) -> TableReference<'a> {
+    pub fn partial(schema: &str, table: &str) -> TableReference {
         TableReference::Partial {
             schema: schema.into(),
             table: table.into(),
@@ -153,11 +150,7 @@ impl<'a> TableReference<'a> {
     /// Convenience method for creating a [`TableReference::Full`]
     ///
     /// As described on [`TableReference`] this does *NO* parsing at all.
-    pub fn full(
-        catalog: impl Into<Cow<'a, str>>,
-        schema: impl Into<Cow<'a, str>>,
-        table: impl Into<Cow<'a, str>>,
-    ) -> TableReference<'a> {
+    pub fn full(catalog: &str, schema: &str, table: &str) -> TableReference {
         TableReference::Full {
             catalog: catalog.into(),
             schema: schema.into(),
@@ -198,18 +191,19 @@ impl<'a> TableReference<'a> {
     /// fully qualified [`TableReference::Full`] if the table names match.
     pub fn resolved_eq(&self, other: &Self) -> bool {
         match self {
-            TableReference::Bare { table } => table == other.table(),
+            TableReference::Bare { table } => **table == *other.table(),
             TableReference::Partial { schema, table } => {
-                table == other.table() && other.schema().map_or(true, |s| s == schema)
+                **table == *other.table()
+                    && other.schema().map_or(true, |s| *s == **schema)
             }
             TableReference::Full {
                 catalog,
                 schema,
                 table,
             } => {
-                table == other.table()
-                    && other.schema().map_or(true, |s| s == schema)
-                    && other.catalog().map_or(true, |c| c == catalog)
+                **table == *other.table()
+                    && other.schema().map_or(true, |s| *s == **schema)
+                    && other.catalog().map_or(true, |c| *c == **catalog)
             }
         }
     }
@@ -217,9 +211,9 @@ impl<'a> TableReference<'a> {
     /// Given a default catalog and schema, ensure this table reference is fully resolved
     pub fn resolve(
         self,
-        default_catalog: &'a str,
-        default_schema: &'a str,
-    ) -> ResolvedTableReference<'a> {
+        default_catalog: &str,
+        default_schema: &str,
+    ) -> ResolvedTableReference {
         match self {
             Self::Full {
                 catalog,
@@ -246,24 +240,7 @@ impl<'a> TableReference<'a> {
     /// Converts directly into an [`OwnedTableReference`] by cloning
     /// the underlying data.
     pub fn to_owned_reference(&self) -> OwnedTableReference {
-        match self {
-            Self::Full {
-                catalog,
-                schema,
-                table,
-            } => OwnedTableReference::Full {
-                catalog: catalog.to_string().into(),
-                schema: schema.to_string().into(),
-                table: table.to_string().into(),
-            },
-            Self::Partial { schema, table } => OwnedTableReference::Partial {
-                schema: schema.to_string().into(),
-                table: table.to_string().into(),
-            },
-            Self::Bare { table } => OwnedTableReference::Bare {
-                table: table.to_string().into(),
-            },
-        }
+        self.clone()
     }
 
     /// Forms a string where the identifiers are quoted
@@ -298,7 +275,7 @@ impl<'a> TableReference<'a> {
 
     /// Forms a [`TableReference`] by parsing `s` as a multipart SQL
     /// identifier. See docs on [`TableReference`] for more details.
-    pub fn parse_str(s: &'a str) -> Self {
+    pub fn parse_str(s: &str) -> Self {
         let mut parts = parse_identifiers_normalized(s, false);
 
         match parts.len() {
@@ -345,46 +322,29 @@ impl From<String> for OwnedTableReference {
     }
 }
 
-impl<'a> From<&'a OwnedTableReference> for TableReference<'a> {
+impl<'a> From<&'a OwnedTableReference> for TableReference {
     fn from(value: &'a OwnedTableReference) -> Self {
-        match value {
-            OwnedTableReference::Bare { table } => TableReference::Bare {
-                table: Cow::Borrowed(table),
-            },
-            OwnedTableReference::Partial { schema, table } => TableReference::Partial {
-                schema: Cow::Borrowed(schema),
-                table: Cow::Borrowed(table),
-            },
-            OwnedTableReference::Full {
-                catalog,
-                schema,
-                table,
-            } => TableReference::Full {
-                catalog: Cow::Borrowed(catalog),
-                schema: Cow::Borrowed(schema),
-                table: Cow::Borrowed(table),
-            },
-        }
+        value.clone()
     }
 }
 
 /// Parse a string into a TableReference, normalizing where appropriate
 ///
 /// See full details on [`TableReference::parse_str`]
-impl<'a> From<&'a str> for TableReference<'a> {
+impl<'a> From<&'a str> for TableReference {
     fn from(s: &'a str) -> Self {
         Self::parse_str(s)
     }
 }
 
-impl<'a> From<&'a String> for TableReference<'a> {
+impl<'a> From<&'a String> for TableReference {
     fn from(s: &'a String) -> Self {
         Self::parse_str(s)
     }
 }
 
-impl<'a> From<ResolvedTableReference<'a>> for TableReference<'a> {
-    fn from(resolved: ResolvedTableReference<'a>) -> Self {
+impl From<ResolvedTableReference> for TableReference {
+    fn from(resolved: ResolvedTableReference) -> Self {
         Self::Full {
             catalog: resolved.catalog,
             schema: resolved.schema,
@@ -400,29 +360,29 @@ mod tests {
     #[test]
     fn test_table_reference_from_str_normalizes() {
         let expected = TableReference::Full {
-            catalog: Cow::Owned("catalog".to_string()),
-            schema: Cow::Owned("FOO\".bar".to_string()),
-            table: Cow::Owned("table".to_string()),
+            catalog: "catalog".into(),
+            schema: "FOO\".bar".into(),
+            table: "table".into(),
         };
         let actual = TableReference::from("catalog.\"FOO\"\".bar\".TABLE");
         assert_eq!(expected, actual);
 
         let expected = TableReference::Partial {
-            schema: Cow::Owned("FOO\".bar".to_string()),
-            table: Cow::Owned("table".to_string()),
+            schema: "FOO\".bar".into(),
+            table: "table".into(),
         };
         let actual = TableReference::from("\"FOO\"\".bar\".TABLE");
         assert_eq!(expected, actual);
 
         let expected = TableReference::Bare {
-            table: Cow::Owned("table".to_string()),
+            table: "table".into(),
         };
         let actual = TableReference::from("TABLE");
         assert_eq!(expected, actual);
 
         // if fail to parse, take entire input string as identifier
         let expected = TableReference::Bare {
-            table: Cow::Owned("TABLE()".to_string()),
+            table: "TABLE()".into(),
         };
         let actual = TableReference::from("TABLE()");
         assert_eq!(expected, actual);
diff --git a/datafusion/core/src/catalog/listing_schema.rs b/datafusion/core/src/catalog/listing_schema.rs
index f64b43062d2f..a9ae47ec903b 100644
--- a/datafusion/core/src/catalog/listing_schema.rs
+++ b/datafusion/core/src/catalog/listing_schema.rs
@@ -129,7 +129,7 @@ impl ListingSchemaProvider {
             if !self.table_exist(table_name) {
                 let table_url = format!("{}/{}", self.authority, table_path);
 
-                let name = OwnedTableReference::bare(table_name.to_string());
+                let name = OwnedTableReference::bare(table_name);
                 let provider = self
                     .factory
                     .create(
diff --git a/datafusion/core/src/datasource/listing_table_factory.rs b/datafusion/core/src/datasource/listing_table_factory.rs
index b616e0181cfc..c48082954e0e 100644
--- a/datafusion/core/src/datasource/listing_table_factory.rs
+++ b/datafusion/core/src/datasource/listing_table_factory.rs
@@ -184,7 +184,7 @@ mod tests {
         let factory = ListingTableFactory::new();
         let context = SessionContext::new();
         let state = context.state();
-        let name = OwnedTableReference::bare("foo".to_string());
+        let name = OwnedTableReference::bare("foo");
         let cmd = CreateExternalTable {
             name,
             location: csv_file.path().to_str().unwrap().to_string(),
@@ -222,7 +222,7 @@ mod tests {
         let factory = ListingTableFactory::new();
         let context = SessionContext::new();
         let state = context.state();
-        let name = OwnedTableReference::bare("foo".to_string());
+        let name = OwnedTableReference::bare("foo");
 
         let mut options = HashMap::new();
         options.insert("format.schema_infer_max_rec".to_owned(), "1000".to_owned());
diff --git a/datafusion/core/src/execution/context/mod.rs b/datafusion/core/src/execution/context/mod.rs
index 31f390607f04..f8bf0d2ee1e5 100644
--- a/datafusion/core/src/execution/context/mod.rs
+++ b/datafusion/core/src/execution/context/mod.rs
@@ -721,10 +721,7 @@ impl SessionContext {
         }
     }
 
-    fn schema_doesnt_exist_err(
-        &self,
-        schemaref: SchemaReference<'_>,
-    ) -> Result<DataFrame> {
+    fn schema_doesnt_exist_err(&self, schemaref: SchemaReference) -> Result<DataFrame> {
         exec_err!("Schema '{schemaref}' doesn't exist.")
     }
 
@@ -762,7 +759,7 @@ impl SessionContext {
 
     async fn find_and_deregister<'a>(
         &self,
-        table_ref: impl Into<TableReference<'a>>,
+        table_ref: impl Into<TableReference>,
         table_type: TableType,
     ) -> Result<bool> {
         let table_ref = table_ref.into();
@@ -1103,9 +1100,9 @@ impl SessionContext {
     ///
     /// Returns the [`TableProvider`] previously registered for this
     /// reference, if any
-    pub fn register_table<'a>(
-        &'a self,
-        table_ref: impl Into<TableReference<'a>>,
+    pub fn register_table(
+        &self,
+        table_ref: impl Into<TableReference>,
         provider: Arc<dyn TableProvider>,
     ) -> Result<Option<Arc<dyn TableProvider>>> {
         let table_ref = table_ref.into();
@@ -1119,9 +1116,9 @@ impl SessionContext {
     /// Deregisters the given table.
     ///
     /// Returns the registered provider, if any
-    pub fn deregister_table<'a>(
-        &'a self,
-        table_ref: impl Into<TableReference<'a>>,
+    pub fn deregister_table(
+        &self,
+        table_ref: impl Into<TableReference>,
     ) -> Result<Option<Arc<dyn TableProvider>>> {
         let table_ref = table_ref.into();
         let table = table_ref.table().to_owned();
@@ -1132,10 +1129,7 @@ impl SessionContext {
     }
 
     /// Return `true` if the specified table exists in the schema provider.
-    pub fn table_exist<'a>(
-        &'a self,
-        table_ref: impl Into<TableReference<'a>>,
-    ) -> Result<bool> {
+    pub fn table_exist(&self, table_ref: impl Into<TableReference>) -> Result<bool> {
         let table_ref = table_ref.into();
         let table = table_ref.table().to_owned();
         Ok(self
@@ -1154,7 +1148,7 @@ impl SessionContext {
     /// [`register_table`]: SessionContext::register_table
     pub async fn table<'a>(
         &self,
-        table_ref: impl Into<TableReference<'a>>,
+        table_ref: impl Into<TableReference>,
     ) -> Result<DataFrame> {
         let table_ref = table_ref.into();
         let provider = self.table_provider(table_ref.to_owned_reference()).await?;
@@ -1170,7 +1164,7 @@ impl SessionContext {
     /// Return a [`TableProvider`] for the specified table.
     pub async fn table_provider<'a>(
         &self,
-        table_ref: impl Into<TableReference<'a>>,
+        table_ref: impl Into<TableReference>,
     ) -> Result<Arc<dyn TableProvider>> {
         let table_ref = table_ref.into();
         let table = table_ref.table().to_string();
@@ -1518,22 +1512,23 @@ impl SessionState {
             .expect("Failed to register default schema");
     }
 
-    fn resolve_table_ref<'a>(
-        &'a self,
-        table_ref: impl Into<TableReference<'a>>,
-    ) -> ResolvedTableReference<'a> {
+    fn resolve_table_ref(
+        &self,
+        table_ref: impl Into<TableReference>,
+    ) -> ResolvedTableReference {
         let catalog = &self.config_options().catalog;
         table_ref
             .into()
             .resolve(&catalog.default_catalog, &catalog.default_schema)
     }
 
-    pub(crate) fn schema_for_ref<'a>(
-        &'a self,
-        table_ref: impl Into<TableReference<'a>>,
+    pub(crate) fn schema_for_ref(
+        &self,
+        table_ref: impl Into<TableReference>,
     ) -> Result<Arc<dyn SchemaProvider>> {
         let resolved_ref = self.resolve_table_ref(table_ref);
-        if self.config.information_schema() && resolved_ref.schema == INFORMATION_SCHEMA {
+        if self.config.information_schema() && *resolved_ref.schema == *INFORMATION_SCHEMA
+        {
             return Ok(Arc::new(InformationSchemaProvider::new(
                 self.catalog_list.clone(),
             )));
diff --git a/datafusion/core/src/test_util/mod.rs b/datafusion/core/src/test_util/mod.rs
index 3244ad49d1c6..75ef364d01fd 100644
--- a/datafusion/core/src/test_util/mod.rs
+++ b/datafusion/core/src/test_util/mod.rs
@@ -65,7 +65,7 @@ pub fn scan_empty(
 ) -> Result<LogicalPlanBuilder> {
     let table_schema = Arc::new(table_schema.clone());
     let provider = Arc::new(EmptyTable::new(table_schema));
-    let name = TableReference::bare(name.unwrap_or(UNNAMED_TABLE).to_string());
+    let name = TableReference::bare(name.unwrap_or(UNNAMED_TABLE));
     LogicalPlanBuilder::scan(name, provider_as_source(provider), projection)
 }
 
@@ -78,7 +78,7 @@ pub fn scan_empty_with_partitions(
 ) -> Result<LogicalPlanBuilder> {
     let table_schema = Arc::new(table_schema.clone());
     let provider = Arc::new(EmptyTable::new(table_schema).with_partitions(partitions));
-    let name = TableReference::bare(name.unwrap_or(UNNAMED_TABLE).to_string());
+    let name = TableReference::bare(name.unwrap_or(UNNAMED_TABLE));
     LogicalPlanBuilder::scan(name, provider_as_source(provider), projection)
 }
 
diff --git a/datafusion/expr/src/logical_plan/builder.rs b/datafusion/expr/src/logical_plan/builder.rs
index e1f760c6e3f7..ad0fc263ccea 100644
--- a/datafusion/expr/src/logical_plan/builder.rs
+++ b/datafusion/expr/src/logical_plan/builder.rs
@@ -1424,8 +1424,8 @@ pub fn subquery_alias(
 
 /// Create a LogicalPlanBuilder representing a scan of a table with the provided name and schema.
 /// This is mostly used for testing and documentation.
-pub fn table_scan<'a>(
-    name: Option<impl Into<TableReference<'a>>>,
+pub fn table_scan(
+    name: Option<impl Into<TableReference>>,
     table_schema: &Schema,
     projection: Option<Vec<usize>>,
 ) -> Result<LogicalPlanBuilder> {
@@ -1435,8 +1435,8 @@ pub fn table_scan<'a>(
 /// Create a LogicalPlanBuilder representing a scan of a table with the provided name and schema,
 /// and inlined filters.
 /// This is mostly used for testing and documentation.
-pub fn table_scan_with_filters<'a>(
-    name: Option<impl Into<TableReference<'a>>>,
+pub fn table_scan_with_filters(
+    name: Option<impl Into<TableReference>>,
     table_schema: &Schema,
     projection: Option<Vec<usize>>,
     filters: Vec<Expr>,
@@ -1911,7 +1911,7 @@ mod tests {
                 },
                 _,
             )) => {
-                assert_eq!("employee_csv", table);
+                assert_eq!(*"employee_csv", *table);
                 assert_eq!("id", &name);
                 Ok(())
             }
@@ -1941,7 +1941,7 @@ mod tests {
                 },
                 _,
             )) => {
-                assert_eq!("employee_csv", table);
+                assert_eq!(*"employee_csv", *table);
                 assert_eq!("state", &name);
                 Ok(())
             }
diff --git a/datafusion/proto/src/logical_plan/from_proto.rs b/datafusion/proto/src/logical_plan/from_proto.rs
index b39ce41bbe26..1675b9dbbc48 100644
--- a/datafusion/proto/src/logical_plan/from_proto.rs
+++ b/datafusion/proto/src/logical_plan/from_proto.rs
@@ -223,17 +223,17 @@ impl TryFrom<protobuf::OwnedTableReference> for OwnedTableReference {
 
         match table_reference_enum {
             TableReferenceEnum::Bare(protobuf::BareTableReference { table }) => {
-                Ok(OwnedTableReference::bare(table))
+                Ok(OwnedTableReference::bare(&table))
             }
             TableReferenceEnum::Partial(protobuf::PartialTableReference {
                 schema,
                 table,
-            }) => Ok(OwnedTableReference::partial(schema, table)),
+            }) => Ok(OwnedTableReference::partial(&schema, &table)),
             TableReferenceEnum::Full(protobuf::FullTableReference {
                 catalog,
                 schema,
                 table,
-            }) => Ok(OwnedTableReference::full(catalog, schema, table)),
+            }) => Ok(OwnedTableReference::full(&catalog, &schema, &table)),
         }
     }
 }
diff --git a/datafusion/sql/src/expr/identifier.rs b/datafusion/sql/src/expr/identifier.rs
index beb7a133e0eb..1d386b21a11c 100644
--- a/datafusion/sql/src/expr/identifier.rs
+++ b/datafusion/sql/src/expr/identifier.rs
@@ -245,22 +245,22 @@ fn form_identifier(idents: &[String]) -> Result<(Option<TableReference>, &String
         1 => Ok((None, &idents[0])),
         2 => Ok((
             Some(TableReference::Bare {
-                table: (&idents[0]).into(),
+                table: idents[0].clone().into(),
             }),
             &idents[1],
         )),
         3 => Ok((
             Some(TableReference::Partial {
-                schema: (&idents[0]).into(),
-                table: (&idents[1]).into(),
+                schema: idents[0].clone().into(),
+                table: idents[1].clone().into(),
             }),
             &idents[2],
         )),
         4 => Ok((
             Some(TableReference::Full {
-                catalog: (&idents[0]).into(),
-                schema: (&idents[1]).into(),
-                table: (&idents[2]).into(),
+                catalog: idents[0].clone().into(),
+                schema: idents[1].clone().into(),
+                table: idents[2].clone().into(),
             }),
             &idents[3],
         )),
@@ -338,7 +338,7 @@ mod test {
     // where ensure generated search terms are in correct order with correct values
     fn test_generate_schema_search_terms() -> Result<()> {
         type ExpectedItem = (
-            Option<TableReference<'static>>,
+            Option<TableReference>,
             &'static str,
             &'static [&'static str],
         );
diff --git a/datafusion/sql/src/planner.rs b/datafusion/sql/src/planner.rs
index d2182962b98e..0ee7860573dd 100644
--- a/datafusion/sql/src/planner.rs
+++ b/datafusion/sql/src/planner.rs
@@ -307,7 +307,7 @@ impl<'a, S: ContextProvider> SqlToRel<'a, S> {
         let plan = self.apply_expr_alias(plan, alias.columns)?;
 
         LogicalPlanBuilder::from(plan)
-            .alias(TableReference::bare(self.normalizer.normalize(alias.name)))?
+            .alias(TableReference::bare(&self.normalizer.normalize(alias.name)))?
             .build()
     }
 
@@ -530,18 +530,18 @@ pub(crate) fn idents_to_table_reference(
     match taker.0.len() {
         1 => {
             let table = taker.take(enable_normalization);
-            Ok(OwnedTableReference::bare(table))
+            Ok(OwnedTableReference::bare(&table))
         }
         2 => {
             let table = taker.take(enable_normalization);
             let schema = taker.take(enable_normalization);
-            Ok(OwnedTableReference::partial(schema, table))
+            Ok(OwnedTableReference::partial(&schema, &table))
         }
         3 => {
             let table = taker.take(enable_normalization);
             let schema = taker.take(enable_normalization);
             let catalog = taker.take(enable_normalization);
-            Ok(OwnedTableReference::full(catalog, schema, table))
+            Ok(OwnedTableReference::full(&catalog, &schema, &table))
         }
         _ => plan_err!("Unsupported compound identifier '{:?}'", taker.0),
     }
diff --git a/datafusion/sql/src/relation/mod.rs b/datafusion/sql/src/relation/mod.rs
index 987fe85de31d..1e01205ba618 100644
--- a/datafusion/sql/src/relation/mod.rs
+++ b/datafusion/sql/src/relation/mod.rs
@@ -55,7 +55,7 @@ impl<'a, S: ContextProvider> SqlToRel<'a, S> {
                         .get_table_function_source(&tbl_func_name, args)?;
                     let plan = LogicalPlanBuilder::scan(
                         TableReference::Bare {
-                            table: std::borrow::Cow::Borrowed("tmp_table"),
+                            table: "tmp_table".into(),
                         },
                         provider,
                         None,
diff --git a/datafusion/sql/src/statement.rs b/datafusion/sql/src/statement.rs
index 69d1b71e4fe8..84dab9067848 100644
--- a/datafusion/sql/src/statement.rs
+++ b/datafusion/sql/src/statement.rs
@@ -994,7 +994,7 @@ impl<'a, S: ContextProvider> SqlToRel<'a, S> {
             self.build_order_by(order_exprs, &df_schema, &mut planner_context)?;
 
         // External tables do not support schemas at the moment, so the name is just a table name
-        let name = OwnedTableReference::bare(name);
+        let name = OwnedTableReference::bare(&name);
         let constraints =
             Constraints::new_from_table_constraints(&all_constraints, &df_schema)?;
         Ok(LogicalPlan::Ddl(DdlStatement::CreateExternalTable(
diff --git a/datafusion/substrait/src/logical_plan/consumer.rs b/datafusion/substrait/src/logical_plan/consumer.rs
index 54324658a1ad..e68f3f992817 100644
--- a/datafusion/substrait/src/logical_plan/consumer.rs
+++ b/datafusion/substrait/src/logical_plan/consumer.rs
@@ -460,16 +460,16 @@ pub async fn from_substrait_rel(
                         return plan_err!("No table name found in NamedTable");
                     }
                     1 => TableReference::Bare {
-                        table: (&nt.names[0]).into(),
+                        table: nt.names[0].clone().into(),
                     },
                     2 => TableReference::Partial {
-                        schema: (&nt.names[0]).into(),
-                        table: (&nt.names[1]).into(),
+                        schema: nt.names[0].clone().into(),
+                        table: nt.names[1].clone().into(),
                     },
                     _ => TableReference::Full {
-                        catalog: (&nt.names[0]).into(),
-                        schema: (&nt.names[1]).into(),
-                        table: (&nt.names[2]).into(),
+                        catalog: nt.names[0].clone().into(),
+                        schema: nt.names[1].clone().into(),
+                        table: nt.names[2].clone().into(),
                     },
                 };
                 let t = ctx.table(table_reference).await?;
