【问题标题】:PostgreSQL ERROR: 42P01: relation "[Table]" does not existPostgreSQL 错误:42P01:关系“[表]”不存在
【发布时间】:2014-12-25 04:59:13
【问题描述】:

我在使用 PostgreSQL 9.3 和使用 qoutes 创建的表时遇到了这个奇怪的问题。例如,如果我使用 qoutes 创建一个表:

create table "TEST" ("Col1" bigint);

该表已正确创建,当在 pgAdminIII 的 SQL 窗格中查看时,我可以看到引号被保留。但是当我查询数据库以查找所有可用表的列表时(使用下面的查询),我看到结果不包含表名周围的引号。

select table_schema, table_name from information_schema.tables where not table_schema='pg_catalog' and not table_schema='information_schema';

由于表是用引号创建的,我不能直接使用从上述查询返回的表名,因为它没有加引号并在标题中发布错误。

我可以尝试在所有查询中用引号将表名括起来,但我不确定它是否会一直有效。我正在寻找一种方法来获取结果中用引号引起来的表名列表。

我在列名方面也遇到了同样的问题,但我希望如果我能找到表名问题的解决方案,类似的解决方案也适用于列名。

【问题讨论】:

    标签: sql postgresql postgis quoted-identifier


    【解决方案1】:

    您有两个选择: - 没有引号:那么一切都会自动小写且不区分大小写 - 带引号:从现在开始,所有内容都区分大小写。

    我强烈建议不要使用引号并使 PostgreSQL 的行为不区分大小写。它让生活变得如此轻松。一旦你开始引用,你必须在任何地方使用它,因为 PostgreSQL 将开始非常精确。

    一些例子:

       TEST = test       <-- non case sensitive
       "Test" <> Test    <-- first is precise, second one is turned to lower case
       "Test" = "Test"   <-- will work
       "test" = TEST     <-- should work; but you are just lucky.
    

    真的要不惜一切代价避免这种诡计。对象名称使用 7 位 ascii。

    【讨论】:

    • 同意在 PostgreSQL 中不使用引号会使生活更轻松,但在我的情况下并不总是可行,因为我的应用程序不创建数据库。它应该能够从第三方 PostgreSQL 数据库中读取数据,并且我无法控制其他人如何创建表。无论如何,令人惊讶的是 PostgreSQL 并没有告诉我某个表是用引号创建的,但是当我在查询中使用未加引号的表名时,它不允许这样做。
    • 只要有一个非小写字母,它就会自动知道使用了引号。所以如果一个表被列为 Test 左右,这已经意味着你必须区分大小写。
    • 我认为这是最后一个选项,因为如果 PostgreSQL 本身可以告诉我表是否包含引号或不是。
    【解决方案2】:

    在使用 npg 包作为数据存储 ORM 时,您希望 ORM 框架(在我们的例子中为实体框架)生成 sql 语句,您可能会遇到关系“表名”不存在的 PostgreSQL 异常

    要么未创建表,要么生成的 SQL 语句缺少某些内容。尝试使用 Visual Studio 进行调试,您会看到架构名称没有领先于表名称

    SELECT "ID", "Name", "CreatedBy", "CreatedDate" 
    FROM "TestTable"; 
    

    而 PostgreSQL 需要模式名称。解决方法是在 DBContext 类中重写 OnModelCreating 方法并添加 modelBuilder.HasDefaultSchema("SchemaName"); 并执行应该如下所示的基本构造函数

    protected override void OnModelCreating(ModelBuilder modelBuilder)   {             
      modelBuilder.HasDefaultSchema("PartyDataManager");                  
      base.OnModelCreating(modelBuilder);         
    }
    

    【讨论】:

      【解决方案3】:

      用于在 SQL 语句字符串中适当地引用标识符的字符串函数是 quote_ident(),它引用了 good example(与相关的 quote_literal() 结合使用)。

      使用您的示例,并混合其他结果:

      select
         quote_ident(table_schema) as table_schema,
         quote_ident(table_name) as table_name
      ...
      
       table_schema |    table_name
      --------------+------------------
       ...
       public       | good_name
       public       | "table"
       public       | some_table
       public       | "something else"
       public       | "Tom's work"
       public       | "TEST"
       ...
      

      【讨论】:

        【解决方案4】:

        就我而言。数据库中的表必须小写...更改名称 dataTable 做数据表帮助

        【讨论】:

        猜你喜欢
        • 2011-02-13
        • 2020-09-19
        • 2019-06-10
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多