数据库管理员

希望提高数据库技能并向社区中的其他人学习的数据库专业人员的问答

3
服务器重新启动后,SQL Server分布式可用性组数据库未同步
我们已经准备好在SQL Server上执行大型升级,并注意到我正在尝试解决的Distributed Availability Groups的一些异常行为,然后再进行下一步。 上个月,我将远程辅助服务器从SQL Server 2016升级到SQL Server2017。该服务器是多个分布式可用性组(DAG)和单独的可用性组(AG)的一部分。升级该服务器时,我们没有意识到它会进入无法读取的状态,因此在过去的一个月中,我们仅依赖主服务器。 作为即将进行的升级的一部分,我将CU 4修补程序应用于服务器并重新启动了它。当服务器重新联机时,刚刚打补丁的辅助服务器显示所有DAG / AG都在同步,没有任何问题。 但是,小学的故事却截然不同。据报道 单独的AG正在同步,没有任何问题 但是DAG处于“ 不同步/不正常”状态 最初出现恐慌之后,我尝试了以下操作以使DAG中的内容再次同步: 从主服务器开始,我停止并恢复了数据移动。这没有开始同步数据。 在第二个(我刚刚打过补丁的)上,我运行了ALTER DATABASE [<database] SET HADR RESUME;-执行时没有错误,但是没有恢复任何同步 我最后一次再次同步数据的尝试是登录到辅助数据库,然后手动重新启动SQL Server服务。手动重新启动服务似乎有些极端,因为我希望重新启动服务器就足够了。 是否有人遇到过重启后DAG无法开始同步到辅助服务器的问题?如果是这样,如何解决? 我同时检查了SQL Server错误日志和辅助服务器上的事件查看器,没有发现异常。

2
触发器每次都编译吗?
我们正在对CPU利用率高的服务器进行故障排除。在发现查询并非真正引起查询之后,我们开始研究编译。 性能监视器显示少于50次编译/秒和少于15次重新编译/秒。 在运行XE会话以查找编译之后,我们每秒看到数千个编译。 该系统正在使用触发器来审核更改。大多数编译是由于触发器引起的。触发器参考sys.dm_tran_active_transactions。 我们的第一个想法是,在触发器中引用DMV会使它每次都编译,或者仅此特定DMV会导致它编译。因此,我开始测试该理论。它确实每次都编译,但是当它不引用DMV而是硬编码一个值时,我没有检查触发器是否在每次触发时都编译。每次触发时它仍在编译。放下触发器将停止编译。 我们在XE会话中使用sqlserver.query_pre_execution_showplan来跟踪编译。为什么与PerfMon计数器之间存在差异? 每次触发运行时,您都会收到一个编译事件是否正常? 复制脚本: CREATE TABLE t1 (transaction_id int, Column2 varchar(100)); CREATE TABLE t2 (Column1 varchar(max), Column2 varchar(100)); GO CREATE TRIGGER t2_ins ON t2 AFTER INSERT AS INSERT INTO t1 SELECT (SELECT TOP 1 transaction_id FROM sys.dm_tran_active_transactions), Column2 FROM inserted; GO --Both of these show compilation …

4
索引空间大于数据空间是否不好?
我经常需要对没有正确索引的大型表运行查询。因此,我要求DBA创建此类索引。他要做的第一件事是查看表统计信息,并查看索引空间大小。 他经常告诉我找到替代解决方案,因为“索引已经大于表”。他认为索引必须小于数据,因为他告诉我“您见过书中的索引吗?它比书本小得多,这就是表索引应该的样子”。 我认为他的理念不正确,但是我不能挑战他,因为他是首席DBA,而我是一名开发人员。我觉得如果查询需要索引,则应该只创建索引,而不是查找只会使SP变得不可读和无法维护的“替代方法”。 我只选择必填列。问题是我按日期过滤,因此引擎必须进行表扫描以匹配列。该查询每天晚上运行一次,以收集统计信息,但是运行需要15分钟(我们有另一条严格的规则:任何过程都不应超过3分钟)。 DBA向我显示了索引统计信息。该表上大约有10个索引,其中只有6个被使用(统计数据显示零命中4个)。这是一个大型系统,有20多个开发人员参与。索引是出于任何原因而创建的,并且可能不再使用。 我们需要支持SQL Server 2008,因为这就是运行测试数据库的基础。但是客户都在2014年和2016年。
22 sql-server  index 

2
使用MAX文字或更具体的小字体
有人正在查看我的DDL代码以创建表,并提出了建议,当他们看到我看到使用VARCHAR(256)文本字段时,我希望它很小,例如名字或其他名称,我应该始终使用VARCHAR(MAX)并链接为什么使用varchar(max )。我读了它,但它似乎过时了,因为它专注于2005年,并且似乎没有提供任何真正的理由在所有文本字段上每行可能分配多达2 GB的空间。 从性能,存储等方面来看,应该如何决定是否VARCHAR(MAX)对现代版本的SQL Server 使用或更小的更具体的类型?(例如,2008、2012、2014)

2
在哪里可以找到SQL的第一个标准化SQL-86?
这个问题是不同的,但与寻找SQL-89的请求类似。 SQL的第一稿标记为SQL-86。对此有许多参考。可以下载吗?维基百科甚至没有页面。由于历史原因,我对此感兴趣。 好像也叫 ANSI X3.135-1986 CAN / CSA Z243.47-88 ISO 9075:1987 SQL / 1 NBS FIPS 127 ANSI技术委员会X3H2在此期间的文档中引用了该规范。 我知道有webstore.ansi.org,但是找不到该X3.135-1986文档。但是,我可以X3.168-1989在X3.135-1992 Searching for 下找到可用的规格both X3.168,并且X3.135不允许我购买1986年的规格。

1
重建索引时何时使用sort_in_tempdb?
我们正在讨论是否对DW表使用SORT_IN_TEMPDB选项。我的理解是,使用此选项时会有更多的写入,尽管它们的顺序更大。我们有一个SAN(众所周知,它有时速度很慢),因此在我们的情况下,我们希望尽可能地限制写入次数。我相信tempdb位于单独的LUN(磁盘集)上。 我们的数据文件和tempdb文件中都有足够的磁盘空间。在这种情况下,我们可以从使用SORT_IN_TEMPDB中受益吗? 令我震惊的是对此答案的评论 重建索引时,您将需要索引空间的两倍+ 20%进行排序。因此,通常来说,要重建数据库中的每个索引,您只需要数据库中最大索引的120%。如果您使用SORT_IN_TEMPDB,则只能赢20%,您的数据文件中仍然需要100%的附加收入。此外,在tempdb中使用sort会大大增加您的IO负载,因为您现在不再将索引一次写入数据文件,而是一次将其写入tempdb,然后再将其写入数据文件。因此,这并不总是理想的。 我们绝对不希望通过慢速/可能配置错误的SAN增加IO负载。 最好的测试方法是什么?通过简单地重建带有和不带有该选项的表并记录时间? 编辑:我们有8个tempdb文件,每个15GB。我们确实设置了TF 1117/1118标志,并且启用了IFI。当前,我们使用sort_in_tempdb选项(不带该选项)进行混合重建。 谢谢! SQL Server 2012企业版


4
如何删除SSMS中的换行符?
我正在处理如下所示的SQL create procedure as begin 请注意,例如as和之间的差距很大begin。 如何删除这些?我使用了SQL格式化程序,但这不起作用。
22 sql-server  ssms 

1
搜寻,然后您应扫描…在分区表上
我已经在Itzik Ben-Gan的 PCMag中阅读了这些文章: 搜寻并您应扫描第一部分:当优化程序未优化 搜寻时,您应扫描第二部分:升序键 我目前所有分区表都遇到“最大分组”问题。我们使用Itzik Ben-Gan提供的技巧来获取max(ID),但有时它无法运行: DECLARE @MaxIDPartitionTable BIGINT SELECT @MaxIDPartitionTable = ISNULL(MAX(IDPartitionedTable), 0) FROM ( SELECT * FROM ( SELECT partition_number PartitionNumber FROM sys.partitions WHERE object_id = OBJECT_ID('fct.MyTable') AND index_id = 1 ) T1 CROSS APPLY ( SELECT ISNULL(MAX(UpdatedID), 0) AS IDPartitionedTable FROM fct.MyTable s WHERE $PARTITION.PF_MyTable(s.PCTimeStamp) = …

2
是否可以强制优化器在此分区视图中消除不相关的表?
我正在测试大型表的不同体系结构,并且看到的一个建议是使用分区视图,即将大型表分解为一系列较小的“分区”表。 1,2,3,4 在测试这种方法时,我发现有些东西对我来说并没有太大意义。当我在事实视图的“分区列”上进行过滤时,优化程序仅在相关表上进行搜索。此外,如果我在维度表的该列上进行过滤,则优化程序会消除不必要的表。 但是,如果我在维度的其他方面进行过滤,则优化器将在每个基本表的PK / CI上进行搜索。 这是有问题的查询: select od.[Year], AvgValue = avg(ObservationValue) from dbo.v_Observation o join dbo.ObservationDates od on o.ObservationDateKey = od.DateKey where o.ObservationDateKey >= 20000101 and o.ObservationDateKey <= 20051231 group by od.[Year]; select od.[Year], AvgValue = avg(ObservationValue) from dbo.v_Observation o join dbo.ObservationDates od on o.ObservationDateKey = od.DateKey where od.DateKey …

2
如何存储时间序列数据
我有一个时间序列数据集(如果我错了,请纠正我),该数据集具有许多关联值。 一个示例是对汽车进行建模并在旅途中跟踪其各种属性。例如: 时间戳| 速度 行驶距离| 温度| 等等 什么是存储此数据的最佳方法,以便Web应用程序可以有效地查询字段以查找最大值,最小值并绘制随时间变化的每个数据集? 我开始分析数据转储并缓存结果,这样就永远不必存储它们了。但是,经过一番尝试之后,由于内存限制,此解决方案似乎无法长期扩展,如果要清除缓存,则需要重新解析并重新缓存所有数据。 另外,假设每秒跟踪数据的可能性极低,可能超过10小时,那么通常建议通过每N秒采样一次来截断数据集吗?

1
插入与OUTPUT相关的子查询表
我正在修改数据库的结构。表FinancialInstitution的几列内容必须转移到表Person中。FinancialInstitution通过外键链接到“人”。每个金融机构都需要其相应人员的ID。因此,对于在Person中插入的每个新行,此新行的ID(IDENTITY)必须复制回FinancialInstitution的相应行中。 显而易见的方法是迭代的T-SQL代码。但是我有兴趣知道是否只有基于集合的操作才有可能做到这一点。 我以为这样的请求的内部层是这样的: INSERT INTO Person (Street1, Number1, City1, State1, PostCode1, CountryId1, WorkDirectPhone1, Fax1, Email1) OUTPUT inserted.Id, FinancialInstitution.Id SELECT Id, Street, Number, City, [State], PostCode, CountryId, PhoneNumber, Fax, Email FROM FinancialInstitution; 不幸的是,看来OUTPUT无法以这种方式建立关联...

2
通过网络以较低的停机时间迁移大型SQL Server数据库的最佳方法
问题定义 我们的数据库服务器需要转移到另一个数据中心。它在Microsoft SQL Server 2012 Enterprise(64位)上运行,并包含两个大约2TB和1TB的数据库。 为此,几乎没有停机时间甚至没有停机时间将是理想的。 工作量 这些数据库用于.NET网站,并且会不断更新。 周末不可用它是可以接受的。在切换到新数据库之前,当前正在使用的数据库将保持唯一。 理想情况下,只需更改DNS条目以指向新的数据库服务器,同时确保不更新数据库,即可进行该切换。 此外,只要将从一台服务器切换到另一台服务器的停机时间(停机时间)保持在较低水平,此操作所花费的时间并不重要。 考虑的方法 备份还原 过去已经做到了这一点,但是即使通过内部网络完成,也要花费大量的停机时间,因此比通过Internet 更有效 日志传送 据我了解,该方法将通过配置主/从服务器并将主数据库的精确副本传输到只读的从服务器,从而最大程度地减少停机时间。如上所述,不需要访问从属服务器,我们只需要一种在不破坏数据的情况下拥有主数据库副本的方法。 就资源利用率而言,它似乎也相当有效,并且不会对主服务器性能产生太大影响。 我对这种方法可能不对,请随时纠正我。 数据库镜像 我不太了解这种方法,但似乎是一个有效的选择。不需要实时同步,并且主机的性能非常重要,因此,如果选择这种方法,异步将是必经之路。 还有其他选择吗? 该服务器直接在裸机硬件上运行,因此不幸的是不能选择较低级别的解决方案。也许有更好的方法可以做到这一点? 约束条件 如上所述,这些数据库很大,难以维护,但这是另一个问题。 SQL Server的版本将相同(Microsoft SQL Server 2012 Enterprise 64位)。 它必须在两个数据中心之间通过网络传输,因此很有可能在Internet上传输。不幸的是,无法将磁盘从一个站点发送到另一个站点进行初始同步。为传输提供某种安全性将是理想的,但是我们会尽力解决这种情况。 这应该可以很好地概述我们对这项任务的需求,希望你们中的某些人不得不面对这种情况。

2
PostgreSQL检查点会发生什么?
这是我的检查点日志的一部分: 2014-03-26 11:51:29.341 CDT,,,18682,,532854fc.48fa,4985,,2014-03-18 09:15:24 CDT,,0,LOG,00000,"checkpoint complete: wrote 15047 buffers (1.4%); 0 transaction log file(s) added, 0 removed, 30 recycled; write=68.980 s, sync=1.542 s, total=70.548 s; sync files=925, longest=0.216 s, average=0.001 s",,,,,,,,,"" 2014-03-26 11:56:05.430 CDT,,,18682,,532854fc.48fa,4987,,2014-03-18 09:15:24 CDT,,0,LOG,00000,"checkpoint complete: wrote 16774 buffers (1.6%); 0 transaction log file(s) added, 0 removed, 31 …
22 postgresql 

6
在30,000,000行表上的DELETE命令未完成
我继承了一个数据库,并希望清理并加快它的速度。我有一个表,其中包含30,000,000行,由于代表程序员的错误,其中许多行都是垃圾数据。在添加任何新的,更优化的索引之前,我已将表从MyISAM转换为InnoDB,并希望删除很多包含垃圾数据的行。 数据库是MySQL 5.0,我具有对该服务器的root访问权限。我首先通过Adminer运行这些命令,然后通过phpMyAdmin运行,结果均相同。 我正在运行的命令是, DELETE FROM `tablename` WHERE `columnname` LIKE '-%' 本质上,删除此列中以破折号开头的所有内容-。 它运行大约3-5分钟,然后当我查看进程列表时,它就消失了。 然后我跑 SELECT * FROM `tablename` WHERE `columnname` LIKE '-%' 它返回数百万行。 为什么我的删除语句没有完成? PS,我知道MySQL 5.0是过时的。我正在努力将数据库移至MySQL 5.6 w InnoDB(也许是MariaDB 10 w XtraDB),但是直到发生这种情况之前,我一直希望使用DB来解决此问题。 - 编辑已删除,请参阅我的答案。

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.