标签: t-sql

如何使用 xp_fixeddrives 创建存储过程?

我需要一个存储过程来检查 2 个链接服务器中的可用空间。(服务器是手动链接的)。我想出了这样的查询并使用 sql server 2008

ALTER PROCEDURE freespace
AS
BEGIN
    CREATE Table #freespace(drive VARCHAR(50),freedrivespace VARCHAR(50));
    DECLARE @servername VARCHAR(50);
    DECLARE @sql VARCHAR(100);
    DECLARE @space  CURSOR;
    SET @space= CURSOR FOR
    SELECT Name FROM SERVERNAME;
    OPEN @space;
    FETCH NEXT
    FROM @space INTO @servername;
    WHILE @@FETCH_STATUS=0
    BEGIN


    SET @sql = '['+@servername+']...xp_fixeddrives';
    INSERT INTO #freespace
    EXEC(@sql);
    FETCH NEXT FROM @space INTO @servername;
    END
    CLOSE @space;
    DEALLOCATE @space;
END
Run Code Online (Sandbox Code Playgroud)

servername表由链接服务器的 servername 组成,如 server1、server2。

当我运行此查询时,会显示如下错误:

Msg 7202, Level 11, State 2, Line 1
Could …
Run Code Online (Sandbox Code Playgroud)

sql-server stored-procedures t-sql

5
推荐指数
1
解决办法
4078
查看次数

创建作业以在表值大于 x 时使用 sp_send_dbmail 发送警报

问题

SMScounter.Counter用于从服务累积使用。该服务的编程上限为 1000。我想在超出此上限时提醒用户。

表创建

CREATE TABLE [dbo].[SMSCounter](
  [Counter] [int] NOT NULL,
  [CounterDate] [datetime] NOT NULL )
Run Code Online (Sandbox Code Playgroud)

示例数据

380, 2012-09-10 00:00:00.000
177, 2012-10-14 00:00:00.000
999, 2012-11-16 00:00:00.000
Run Code Online (Sandbox Code Playgroud)

作业脚本

下面的脚本是我尝试创建一个计划作业,如果SMScounter.Counter大于 950 ,它将每小时检查一次。

USE DATABASEname
select (Counter) as CHECKVALUE from SMSCounter where smscounter.CounterDate  = DATEADD(dd, DATEDIFF(dd, 0, GETDATE()),0)    
IF CHECKVALUE > 950

BEGIN

EXEC msdb.dbo.sp_send_dbmail
  @recipients=N'scott@mydomain.com',
  @body='1000 Daily SMS cap near', 
  @subject ='1000 Daily SMS cap near',
  @profile_name ='SCOTT',
  @query =
    'USE DATABASEname
     (select * from SMSCounter where CounterDate …
Run Code Online (Sandbox Code Playgroud)

sql-server t-sql database-mail alerts

5
推荐指数
1
解决办法
2万
查看次数

设置变量时是否有使用 NOT IN (1,2,3) 语法的紧凑方法?

像 NOT IN (1,2,3) 这样的表达式在 where 子句中是有效的:

SELECT foo FROM bar WHERE 
  ((record_type NOT IN (2, 3, 7, 18, 19, 20, 21,12,13,22))
Run Code Online (Sandbox Code Playgroud)

但是,如果我想将一个由上述检查组成的复杂表达式从 WHERE 子句移动到 SET @Var= 语句,有没有办法做到这一点而无需像这样重写它:

declare @record_type int
set  @record_type  = 1

declare @ignoretype bit
IF    (@record_type <> 2)and(@record_type <> 3)and(@record_type <> 7)and
      (@record_type <> 12)and(@record_type <> 13)and
      ( (@record_type < 18) or (@record_type > 22))
     set @ignoretype=1
else
     set @ignoretype=0
Run Code Online (Sandbox Code Playgroud)

我觉得过去适合在一个可读行中的内容现在是一个巨大的混乱,这真的很糟糕。我是否在 SQL 中遗漏了一些与“NOT IN (1,2,3)”等效的语法,这些语法适用于set @var =IF表达式?我会把上面写成:

select @ignoretype = (@record_type <> …
Run Code Online (Sandbox Code Playgroud)

sql-server t-sql

5
推荐指数
1
解决办法
289
查看次数

临时表上的非聚集索引

我正在研究各种查询优化技术。我仅通过在包含一列(用于多个 where 条件)的表上添加非聚集索引将查询执行时间从 1 分钟减少到 12 秒,但 DBA 对添加索引非常挑剔。

我想知道通过在临时表而不是实际表上添加 NCI 是否有任何区别。如果是,如何?如果否,为什么?

sql-server t-sql

5
推荐指数
2
解决办法
5万
查看次数

以编程方式查找无法在线重建的索引

我正在使用 T-SQL 自动重建和重新组织索引。我遇到了无法在线重建的索引问题。发生这种情况主要是因为包含 ntext/nvarchar 列。

有没有办法以编程方式将它们标识为该语句的一部分?对 WHERE 谓词的补充

SELECT 
--TOP 20
OBJECT_NAME(IPS.OBJECT_ID) AS [TableName], avg_fragmentation_in_percent, SI.name         [IndexName],  
schema_name(ST.schema_id) AS [SchemaName], 0 AS IsProcessed 
INTO #FramentedTableList 
FROM sys.dm_db_index_physical_stats(DB_ID(), NULL, NULL, NULL , NULL) IPS 
JOIN sys.tables ST WITH (nolock) ON IPS.OBJECT_ID = ST.OBJECT_ID 
JOIN sys.indexes SI WITH (nolock) ON IPS.OBJECT_ID = SI.OBJECT_ID AND IPS.index_id =   SI.index_id 
WHERE ST.is_ms_shipped = 0 AND SI.name IS NOT NULL 
AND avg_fragmentation_in_percent >= CONVERT(DECIMAL,   @FragmentationThresholdForReorganizeTableLowerLimit) 
ORDER BY avg_fragmentation_in_percent DESC 
Run Code Online (Sandbox Code Playgroud)

index sql-server t-sql

5
推荐指数
1
解决办法
2413
查看次数

带有参数化 LIKE 的意外表扫描

参数化LIKE语句时,我在 SQL Server 2005 上遇到了针对堆表的意外表扫描......但是当与变量相同的值被硬编码时,会发生预期的索引查找。

这个问题只发生在这种特定的情况下......所以我对如何解决这个问题并不感到困惑,我对为什么会发生这种情况感到困惑。

以下 T-SQL 应在 SQL Server 2005 上重现该问题:

IF (OBJECT_ID('tempdb.dbo.#tblTest') IS NOT NULL)
    DROP TABLE dbo.#tblTest
GO

CREATE TABLE dbo.#tblTest (
    ID INT IDENTITY(1, 1),
    SerialNumber VARCHAR(50)
)
GO

-- Populate the table with 10,000 rows
SET NOCOUNT ON
DECLARE @i INT
SET @i = 0

WHILE @i < 10000
BEGIN
    INSERT INTO dbo.#tblTest VALUES(CAST(@i AS VARCHAR(10)))
    SET @i = @i + 1
END
GO

-- To recreate the issue, the …
Run Code Online (Sandbox Code Playgroud)

sql-server-2005 sql-server t-sql

5
推荐指数
1
解决办法
1130
查看次数

表值函数中的条件 WHERE 子句

我有一个表值函数

    CREATE FUNCTION [dbo].[DateRange] 
    (
        @StartDate date,
        @EndDate date,
        @Location varchar(25),
        @Device varchar(25)
    ) 
    RETURNS TABLE 
    AS
    RETURN 
    (
        SELECT *
        FROM MyTable
        WHERE Date < @EndDate AND
              Date > @StartDate AND
              Location = @Location AND
              Device = @Device 

    );
Run Code Online (Sandbox Code Playgroud)

现在我想让用户选择使用 NULL 作为位置参数和/或设备参数,以便他/她获取与位置和设备无关的所有数据

什么是最优雅和最有效的方式来做到这一点?

t-sql sql-server-2012

5
推荐指数
1
解决办法
5171
查看次数

我们如何从触发器内部获取表名?

我需要将表名从触发器传递到过程。

ALTER TRIGGER [dbo].[Trg_ProjectCreation] 
   ON  [dbo].[Projects] 
   AFTER INSERT
AS 
BEGIN   
    SET NOCOUNT ON; 
 -- procedure call 
    exec Proc_Test @Tablename (not need to hardcode)
END
Run Code Online (Sandbox Code Playgroud)

我想知道有什么方法可以从触发器本身获取表名。我需要它是动态的,因为当表的名称更改时,我不想更改我的代码。

trigger sql-server-2008 t-sql

5
推荐指数
1
解决办法
2万
查看次数

为什么 SQL Server 2008 R2 在使用批量插入时插入无效的日期时间?

我想 在 SQL Server 2008 R2 上使用T-SQL BULK INSERT插入带有可选日期时间值(每行)的行。

一张表可能如下所示:

CREATE TABLE [dbo].[tbl_bulk_insert_datetime_issue] (
    [id] [int] NOT NULL,
    [description] [varchar](20) NOT NULL,
    [datetime] [datetime] NULL,
CONSTRAINT [pk_bulk_insert_datetime_issue] PRIMARY KEY CLUSTERED (
    [id] ASC
))
Run Code Online (Sandbox Code Playgroud)

插入批次:

BULK
INSERT [dbo].[tbl_bulk_insert_datetime_issue]
FROM 'C:\temp\bulkinsertsample.csv'
WITH
(
    FIELDTERMINATOR=';'
)
Run Code Online (Sandbox Code Playgroud)

如果我要插入以下 CSV 内容:

1;row01;
2;row02;20130401
3;row03;
4;row04;20130515
Run Code Online (Sandbox Code Playgroud)

表的内容已按预期解析和插入:

id          description          datetime
----------- -------------------- -----------------------
1           row01                NULL
2           row02                2013-04-01 00:00:00.000
3           row03                NULL
4           row04                2013-05-15 00:00:00.000
Run Code Online (Sandbox Code Playgroud)


但是如果 CSV 文件包含可选日期时间的无效数据

1;row01;
2;row02;20130401
3;row03;not_a_datetime …
Run Code Online (Sandbox Code Playgroud)

t-sql sql-server-2008-r2 datetime bulk-insert

5
推荐指数
1
解决办法
3218
查看次数

为什么我无法查看 Web 应用程序创建的 SQL Server 数据库?

我有一个 ASP.NET MVC Web 应用程序部署到 Windows Server 2012 机器上的 IIS。当应用程序第一次启动时,它会在必要时通过实体框架创建它需要的数据库和表。这一切正常,现在我想通过 SQL Server Management Studio 对数据库进行一些管理。但是,当我打开该工具时,我只能看到系统数据库。如果我从连接字符串中删除“User Instance=true”并让应用程序再次创建数据库,我就可以看到数据库。

当User Instance=true 在连接字符串中时,为什么我无法查看Web 应用程序创建的数据库? 如果我使用具有所有角色的帐户通过 Management Studio 查看服务器实例,我希望它能够查看任何和所有数据库。

一些可能有帮助的细节:

该应用程序在 Web.config 中使用以下连接字符串:

<add name="DefaultConnection" connectionString="Data Source=.\SqlExpress; 
  Initial Catalog=Foo.Dashboard;  Integrated Security=SSPI;User Instance=true" 
  providerName="System.Data.SqlClient" />
Run Code Online (Sandbox Code Playgroud)

在IIS中,应用程序池设置为与身份运行LocalServiceLoad User Profile设置True。在 SQL Server Express 上,我们为该Local Service帐户添加了一个登录名并为其分配了dbcreator角色。当应用程序启动时,它就能够创建数据库和表,一切似乎都在运行。

然后我使用远程桌面连接到服务器并打开 SQL Server Management Studio。要连接到数据库,我输入.\SQLEXPRESS服务器名称并使用Windows Authentication. 然后我连接并且只看到系统数据库。我已将所有可能的数据库角色添加到我的登录名中,并且我看到我VIEW ANY DATABASE在有效选项卡中拥有权限。

sql-server ssms entity-framework t-sql sql-server-express

5
推荐指数
1
解决办法
2836
查看次数