什么';在PostgreSQL数据库中定期同步数据的最有效方法是什么?

什么';在PostgreSQL数据库中定期同步数据的最有效方法是什么?,sql,ruby-on-rails,ruby,postgresql,sync,Sql,Ruby On Rails,Ruby,Postgresql,Sync,我的PostgreSQL 9.0.x DB中有一个名为cached_projects的表,我主要通过Rails应用程序访问该表,其模式如下: create_table "cached_projects", :force => true do |t| t.string "name", :null => false t.datetime "created_at", :n

我的PostgreSQL 9.0.x DB中有一个名为
cached_projects
的表,我主要通过Rails应用程序访问该表,其模式如下:

create_table "cached_projects", :force => true do |t|
  t.string   "name",                               :null => false
  t.datetime "created_at",                         :null => false
  t.datetime "updated_at",                         :null => false
  t.boolean  "localization",    :default => false, :null => false
  t.integer  "base_project_id"
end
该表由Rake任务填充,该任务每N分钟运行一次,并执行以下操作:

  • 从SOAPWeb服务查询所有项目记录(此上下文中的“项目”仅由一个名称(字符串)和一对布尔和整数字段组成)
  • 将数据库中的项目列表与SOAP结果同步,丢弃SOAP结果中不再存在的任何记录,并添加找到的任何新记录
进行定期同步最有效的方法是什么?数据库中的行必须与SOAP结果中给出的记录完全匹配,而不需要额外的数据

我可以想出两种解决方案,但不确定哪一种最快(性能是一个问题,因为有成千上万条记录,我希望尽可能频繁地同步):

  • 在每次同步期间,删除
    缓存的\u项目中的所有行
    ,并为通过SOAP服务找到的每个项目插入新的行

    这将实现拥有完全相同的数据集的目标,但是假设数据库中的绝大多数数据不变,那么每次删除约50000行的成本会有多高?在数据库中有这么多的“搅动”是否有负面影响

  • 在每次同步期间,选择
    缓存的\u项目中的所有行,将它们存储在临时哈希变量中。在SOAP记录上循环,对于每个记录,检查它是否已经在DB中(使用临时哈希),保留我们找到的DB记录的ID列表,以便它们可以保留在DB中。比较完所有内容后,为所有新记录插入行,并删除不应再在表中的记录的行

    这是我目前的解决方案,虽然它也准确地反映了数据,但比较Rake任务中的所有记录需要大量计算,每次同步大约需要3-5分钟。(实际上,第一次同步时,当DB表为空时,它会更快,但在后续同步时,它必须与所有行进行比较,这会更慢。)


  • 我愿意接受其他的建议,或者对这些想法的改进。到目前为止,我一直在研究应用程序代码中的解决方案(基于Ruby的rake任务),但我也对将更多逻辑引入数据库本身的想法感兴趣,因为我对这方面的知识不太熟悉。

    如果第一次同步比后续同步快,这意味着将所有数据插入数据库比比较每个数据并修改现有表更快

    我建议您使用
    TRUNCATE
    删除表中的所有记录,而不是删除,然后将所有记录插入表中


    我认为基本问题最好在上面提问。我怀疑解决方案将在我的应用程序代码(Ruby)中实现,而不是在DB或SQL中实现,因此我将其发布在这里,但也可以在DBA上查看,谢谢。可能的话,但我会根据如何使用基本DBM查询进行更新提出一个问题。这将是最快的I/O和数据传输。您可以将XML转换为数据库中的临时表,然后使用一点SQL进行同步。或者可以更容易/更快地批量替换表,甚至可以将XML转储到新表中,并进行删除/重命名以替换旧表。这对每个人都会更好。服务的负载要小得多。我只是说:)谢谢,这确实比删除整个表要好得多。我相信我最终只会截断整个表,每次都重新插入行,因为这样做非常快。