001/* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to you under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017package gudusoft.gsqlparser.sqlenv; 018 019import gudusoft.gsqlparser.EDbVendor; 020import gudusoft.gsqlparser.ext.sqlnamematcher.SqlNameMatcher; 021import gudusoft.gsqlparser.ext.sqlnamematcher.SqlNameMatchers; 022 023import java.util.EnumMap; 024import java.util.Map; 025 026/** 027 * Factory for creating SqlNameMatcher instances per database vendor and object type. 028 * 029 * <p>This class bridges GSP's existing case sensitivity configuration (stored in 030 * TSQLEnv's EnumMaps) to the SqlNameMatcher framework.</p> 031 * 032 * <p>Design rationale: Instead of duplicating vendor-specific case rules, this factory 033 * reads from TSQLEnv's existing static maps and creates appropriate matchers on demand.</p> 034 * 035 * @since 3.2.0.3 (Phase 1) 036 */ 037public class NamePolicyFactory { 038 039 private final EDbVendor vendor; 040 041 // Cache matchers per type to avoid repeated creation 042 private final Map<ESQLDataObjectType, SqlNameMatcher> matcherCache = 043 new EnumMap<>(ESQLDataObjectType.class); 044 045 /** 046 * Creates a new NamePolicyFactory for the specified database vendor. 047 * 048 * @param vendor the database vendor 049 */ 050 public NamePolicyFactory(EDbVendor vendor) { 051 if (vendor == null) { 052 throw new IllegalArgumentException("vendor cannot be null"); 053 } 054 this.vendor = vendor; 055 } 056 057 /** 058 * Returns the database vendor associated with this factory. 059 * 060 * @return the database vendor 061 */ 062 public EDbVendor getVendor() { 063 return vendor; 064 } 065 066 /** 067 * Gets or creates a SqlNameMatcher for the specified object type. 068 * 069 * <p>The matcher's case sensitivity is determined by querying TSQLEnv's 070 * static maps (columnCollationCaseSensitive, tableCollationCaseSensitive, etc.)</p> 071 * 072 * <p>Results are cached to avoid repeated map lookups.</p> 073 * 074 * @param type the SQL data object type (table, column, function, etc.) 075 * @return a SqlNameMatcher configured for the vendor/type combination 076 */ 077 public SqlNameMatcher getMatcherForType(ESQLDataObjectType type) { 078 // Check cache first 079 SqlNameMatcher cached = matcherCache.get(type); 080 if (cached != null) { 081 return cached; 082 } 083 084 // Create new matcher based on TSQLEnv's existing configuration 085 SqlNameMatcher matcher = createMatcher(type); 086 matcherCache.put(type, matcher); 087 return matcher; 088 } 089 090 /** 091 * Creates a SqlNameMatcher by reading TSQLEnv's case sensitivity maps. 092 * 093 * @param type the object type 094 * @return a newly created SqlNameMatcher 095 */ 096 private SqlNameMatcher createMatcher(ESQLDataObjectType type) { 097 boolean caseSensitive; 098 099 switch (type) { 100 case dotCatalog: 101 case dotSchema: 102 // Catalog and schema use the catalogCollationCaseSensitive map 103 caseSensitive = TSQLEnv.catalogCollationCaseSensitive.get(vendor); 104 break; 105 106 case dotTable: 107 case dotProcedure: 108 case dotTrigger: 109 case dotOraclePackage: 110 // Tables, procedures, triggers, and Oracle packages use tableCollationCaseSensitive 111 caseSensitive = TSQLEnv.tableCollationCaseSensitive.get(vendor); 112 break; 113 114 case dotFunction: 115 // Functions have their own map 116 caseSensitive = TSQLEnv.functionCollationCaseSensitive.get(vendor); 117 break; 118 119 case dotColumn: 120 // Columns have their own map 121 caseSensitive = TSQLEnv.columnCollationCaseSensitive.get(vendor); 122 break; 123 124 default: 125 // Everything else uses the default map 126 caseSensitive = TSQLEnv.defaultCollationCaseSensitive.get(vendor); 127 break; 128 } 129 130 // Create a matcher with the appropriate case sensitivity 131 return SqlNameMatchers.withCaseSensitive(caseSensitive); 132 } 133 134 /** 135 * Convenience method to check if a specific object type is case-sensitive 136 * for this vendor. 137 * 138 * @param type the object type 139 * @return true if case-sensitive, false otherwise 140 */ 141 public boolean isCaseSensitive(ESQLDataObjectType type) { 142 return getMatcherForType(type).isCaseSensitive(); 143 } 144}