Thoát khỏi chế độ người dùng đơn


208

Hiện tại, cơ sở dữ liệu của tôi đang ở chế độ Người dùng đơn. Khi tôi cố gắng mở rộng cơ sở dữ liệu, tôi gặp lỗi:

Cơ sở dữ liệu 'my_db' không truy cập được. (ObjectExplorer)

Ngoài ra, khi tôi cố gắng xóa cơ sở dữ liệu, tôi gặp lỗi:

Thay đổi trạng thái hoặc tùy chọn của cơ sở dữ liệu 'my_db' không thể được thực hiện tại thời điểm này. Cơ sở dữ liệu ở chế độ một người dùng và người dùng hiện đang kết nối với nó.

Làm cách nào để thoát khỏi chế độ một người dùng? Tôi không có bất kỳ người dùng nào sử dụng cơ sở dữ liệu này.

Khi tôi cố duyệt trang web của mình bằng IIS, lỗi tôi gặp là:

Một ngoại lệ chưa được xử lý đã được tạo trong quá trình thực hiện yêu cầu web hiện tại. Thông tin liên quan đến nguồn gốc và vị trí của ngoại lệ có thể được xác định bằng cách sử dụng dấu vết ngăn xếp ngoại lệ bên dưới.

Tôi cảm thấy như thể chế độ một người dùng đang gây ra điều này.

Câu trả lời:


381

SSMS nói chung sử dụng một số kết nối đến cơ sở dữ liệu đằng sau hậu trường.

Bạn sẽ cần phải hủy các kết nối này trước khi thay đổi chế độ truy cập.

Đầu tiên, hãy chắc chắn rằng trình thám hiểm đối tượng được trỏ đến một cơ sở dữ liệu hệ thống như master.

Thứ hai, thực hiện sp_who2 và tìm tất cả các kết nối đến cơ sở dữ liệu 'my_db'. Giết tất cả các kết nối bằng cách thực hiện KILL { session id }trong đó id phiên được SPIDliệt kê bởi sp_who2.

Thứ ba, mở một cửa sổ truy vấn mới.

Thực hiện mã sau đây.

-- Start in master
USE MASTER;

-- Add users
ALTER DATABASE [my_db] SET MULTI_USER
GO

Xem bài viết blog của tôi về quản lý tập tin cơ sở dữ liệu. Điều này đã được viết để di chuyển các tập tin, nhưng quản lý người dùng là như nhau.


2
Khi tôi sử dụng lệnh 'sp_who2', tôi không thấy bất kỳ DBName nào được kết nối với 'my_db' Tôi không giết bất kỳ kết nối nào trong số đó. Sau khi tôi chạy các lệnh, tôi nhận được cùng một lỗi = [: 'Thay đổi trạng thái hoặc tùy chọn của cơ sở dữ liệu' my_db 'không thể được thực hiện tại thời điểm này. Cơ sở dữ liệu ở chế độ một người dùng và người dùng hiện đang kết nối với nó. Msg 5069, Level 16, State 1, Line 1 ALTER DATABASE tuyên bố thất bại '
Liondancer

2
Bạn có chắc chắn rằng bạn đang ở chế độ chính, sp_who2 không hiển thị bất kỳ hàng nào có cơ sở dữ liệu = my_db và trình thám hiểm đối tượng của bạn không có trên my_db.
CRAFTY DBA

1
Hãy thử, ngắt kết nối và kết nối SSMS. Một cái gì đó phải được kết nối với cơ sở dữ liệu đó. Tùy chọn khác là kết nối với bảng điều khiển quản trị chuyên dụng (DAC). Điều này giả định rằng bạn là một sysadmin. Sau đó giết chết các spid vi phạm.
CRAFTY DBA

1
Ngoài ra, tải xuống tập lệnh usp_who2 của tôi ( craftydba.com/wp-content/uploads/2011/09/usp-who2.txt ). Thực hiện nó. Nó đặt tiện ích trong msdb.dbo.usp_who2. Nó lưu kết quả của sp_who2 vào một bảng trong tempdb dưới id người dùng của bạn, lọc theo tên cơ sở dữ liệu. Đăng một hình ảnh của lỗi để giúp chúng tôi nhiều hơn. Chúc may mắn.
DBA CRAFTY

3
Tìm SPID, sử dụng như sau: Kill 100. 100 là số phiên (SPID).
CRAFTY DBA

45

Đầu tiên, tìm và KILLtất cả các quy trình hiện đang chạy.

Sau đó, chạy như sau T-SQLđể đặt cơ sở dữ liệu trong MULTI_USERchế độ.

USE master
GO
DECLARE @kill varchar(max) = '';
SELECT @kill = @kill + 'KILL ' + CONVERT(varchar(10), spid) + '; '
FROM master..sysprocesses 
WHERE spid > 50 AND dbid = DB_ID('<Your_DB_Name>')
EXEC(@kill);

GO
SET DEADLOCK_PRIORITY HIGH
ALTER DATABASE [<Your_DB_Name>] SET MULTI_USER WITH NO_WAIT
ALTER DATABASE [<Your_DB_Name>] SET MULTI_USER WITH ROLLBACK IMMEDIATE
GO

Giải pháp này sẽ không hoạt động với tôi trên SQL Server 2016. Nếu tôi truy vấn master..sys Processes, tôi thấy một số hàng xuất hiện, nhưng sau đó các hàng được thay thế bằng một thông báo lỗi rằng cơ sở dữ liệu đã cho ở chế độ người dùng, v.v.
youcantryreachingme

@youcantryreachingme, vui lòng cung cấp thông báo lỗi bạn gặp trong SQL Server 2016 tại đây để tôi / người khác có thể giúp bạn giải quyết.
Sathish

giống như trong OP: Thay đổi trạng thái hoặc tùy chọn của cơ sở dữ liệu 'my_db' không thể được thực hiện tại thời điểm này. Cơ sở dữ liệu ở chế độ một người dùng và người dùng hiện đang kết nối với nó.
youcantryreachingme

25

Để tắt chế độ Người dùng đơn, hãy thử:

ALTER DATABASE [my_db] SET MULTI_USER

Để chuyển về chế độ Người dùng đơn, bạn có thể sử dụng:

ALTER DATABASE [my_db] SET SINGLE_USER


1
Tôi gặp lỗi: 'Không thể thay đổi trạng thái hoặc tùy chọn của cơ sở dữ liệu' my_db 'tại thời điểm này. Cơ sở dữ liệu ở chế độ một người dùng và người dùng hiện đang kết nối với nó. Msg 5069, Cấp 16, Trạng thái 1, Dòng 1 THAY ĐỔI Tuyên bố thay đổi thất bại. '
Liondancer

1
Bạn có thể dừng và khởi động lại cơ sở dữ liệu (rõ ràng nếu đây không phải là hệ thống sản xuất sẽ ảnh hưởng đến người dùng khác), sau đó thử lại lệnh? Và như @CRAFTYDBA đã nói lệnh nên được thực thi từ cơ sở dữ liệu chủ.
rsbarro

1
Tôi đã mở rộng 'Cơ sở dữ liệu hệ thống' và nhấp chuột phải vào 'chủ' và chọn 'Truy vấn mới' và thử trong cả hai dấu phẩy của bạn và @ CRAFTYDBA. Cùng một lỗi = [
Liondancer

1
Bạn đã thử dừng và khởi động lại cơ sở dữ liệu để hủy kết nối hiện có chưa? Bạn cũng có thể xem tại đây để biết thêm các cách để
hủy

2
Nhấp chuột phải vào máy chủ trong khung bên trái và nhấp vào 'Ngắt kết nối'. Đảm bảo rằng bạn chỉ có một tab SSMS mở trên cơ sở dữ liệu của bạn (nhấp chuột phải và chọn 'Ngắt kết nối các kết nối khác') và sau đó thực hiện câu lệnh. Mỗi tab và thám hiểm đối tượng là một kết nối; bạn chỉ có thể mở một kết nối tới cơ sở dữ liệu (do đó, mode chế độ một người dùng '). Người dùng đơn lẻ phải là 'kết nối duy nhất' :) Chúc may mắn
tommy_o

20
  1. Nhấp chuột phải vào cơ sở dữ liệu của bạn trong phần cơ sở dữ liệu
  2. Chọn "Thuộc tính"
  3. Chọn trang "Tùy chọn"
  4. Cuộn xuống "Tùy chọn khác" và thay đổi trường "Hạn chế truy cập"

ảnh chụp màn hình trang tùy chọn của máy chủ sql


1
Giải pháp này sẽ không hoạt động với tôi trên SQL Server 2016. Cố gắng truy cập các thuộc tính cho thấy lỗi cơ sở dữ liệu ở chế độ người dùng và đã có người dùng được kết nối.
youcantryreachingme


8

Tôi đã có cùng một vấn đề và session_id to kill được tìm thấy bằng truy vấn này:

Select request_session_id From sys.dm_tran_locks Where resource_database_id=DB_ID('BI_DB_Rep');

Điều này là hoàn hảo. Tìm thấy SPID phiền phức và đưa DB trở lại trực tuyến. Cảm ơn rất nhiều!
Russell Speight

8

Nhấn CTRL + 1

tìm quá trình khóa cơ sở dữ liệu của bạn. Tìm trong cột dbname cho db của bạn và lưu ý spid. Bây giờ bạn phải thực hiện câu lệnh đó:

kill <your spid>
ALTER DATABASE <your db> SET MULTI_USER;

CTRL + 1 là một phím tắt rất tiện dụng mà tôi không biết!
Tyler Forsythe

7

Sau đây làm việc cho tôi:

USE [master]
SET DEADLOCK_PRIORITY HIGH
exec sp_dboption '[StuckDB]', 'single user', 'FALSE';
ALTER DATABASE [StuckDB] SET MULTI_USER WITH NO_WAIT
ALTER DATABASE [StuckDB] SET MULTI_USER WITH ROLLBACK IMMEDIATE

7

Một lựa chọn khác là:

  • lấy cơ sở dữ liệu ngoại tuyến; trong SMSS, nhấp chuột phải vào cơ sở dữ liệu và chọn Thực hiện ngoại tuyến, đánh dấu 'Thả tất cả các kết nối'
  • chạy ALTER DATABASE [Your_Db] SET MULTI_USER

Của tôi sẽ không cho phép tôi ngoại tuyến, nó chỉ nói rằng nó ở chế độ người dùng duy nhất và người dùng đã được kết nối! (vâng, tôi đã đánh dấu vào "thả tất cả các kết nối"). Tôi đã kết thúc việc tách cơ sở dữ liệu thay thế!
TabbyCool

Tôi đã phải sử dụng tùy chọn này vì không có người dùng nào được kết nối và lệnh KILL sẽ không hoạt động trên kết nối sa.
Derek K

6

Chỉ trong trường hợp nếu ai đó tình cờ bắt gặp chủ đề này thì đây là một giải pháp chống đạn cho SQL Server bị mắc kẹt trong chế độ SINGLE USER MODE

- Nhận ID tiến trình (spid) của kết nối bạn cần
hủy - Thay thế 'DBName' bằng tên thật của DB

SELECT sd.[name], sp.spid, sp.login_time, sp.loginame 
FROM sysprocesses sp 
INNER JOIN sysdatabases sd on sp.dbid = sd.dbid  
WHERE sd.[name] = 'DBName'

Cách khác, bạn cũng có thể sử dụng lệnh Cấm sp_who 'để nhận được spid spid của kết nối mở:

- Hoặc sử dụng SP này thay thế

exec sp_who

- Sau đó, thực hiện các thao tác sau và thay thế [spid] và [DBName] bằng các giá trị chính xác

KILL SpidToKillGoesHere
GO

SET DEADLOCK_PRIORITY HIGH
GO

ALTER DATABASE [DBName] SET MULTI_USER WITH ROLLBACK IMMEDIATE
GO

Cảm ơn thông tin bổ sung, đã tạo ra một sự khác biệt lớn!
Daniel

5

Không chắc điều này có giúp được ai không, nhưng tôi có cùng một vấn đề và không thể tìm thấy quy trình đang giữ tôi lại. Tôi đã đóng SSMS và dừng tất cả các dịch vụ đánh vào trường hợp cục bộ. Sau đó, khi tôi quay lại và chạy exec sp_who2, nó cho tôi thấy thủ phạm. Tôi đã giết tiến trình và có thể khiến Multi_User hoạt động, sau đó khởi động lại các dịch vụ. Chúng tôi đã có IIS nhấn nó cứ sau vài phút / giây để tìm kiếm các gói nhất định.


3

Tôi đã chạy qua cùng một vấn đề sáng nay. Nó hóa ra là một vấn đề đơn giản. Tôi đã mở một cửa sổ truy vấn được đặt thành cơ sở dữ liệu người dùng trong trình thám hiểm đối tượng. Thủ tục lưu trữ sp_who2 không hiển thị sau đó kết nối. Khi tôi đóng nó, tôi có thể đặt nó thành


3

Thêm vào câu trả lời của Jespers , để có hiệu quả hơn nữa:

SET DEADLOCK_PRIORITY 10;-- Be the top dog.

SET DEADLOCK_PRIORITY HIGHsử dụng DEADLOCK_PRIORITY5.

Điều đang xảy ra là các quy trình khác bị bẻ khóa tại cơ sở dữ liệu và, nếu quy trình của bạn có mức thấp hơn DEADLOCK_PRIORITY, thì nó sẽ thua cuộc đua.

Điều này cản trở việc tìm kiếm và tiêu diệt các spid khác (có thể cần phải thực hiện nhiều lần).

Có thể bạn sẽ cần phải chạy ALTER DATABASEnhiều hơn một lần, (nhưng Jesper làm điều đó). Mã sửa đổi:

USE [master]
SET DEADLOCK_PRIORITY HIGH
exec sp_dboption '[StuckDB]', 'single user', 'FALSE';
ALTER DATABASE [StuckDB] SET MULTI_USER WITH NO_WAIT
ALTER DATABASE [StuckDB] SET MULTI_USER WITH ROLLBACK IMMEDIATE

3

Sử dụng tập lệnh này

exec sp_who

Tìm cột dbname và spid

bây giờ thực hiện

kill spid 
go
ALTER DATABASE [DBName]
SET MULTI_USER;

2

Hôm nay tôi gặp phải vấn đề tương tự khi cơ sở dữ liệu của tôi bị thay đổi từ chế độ Nhiều người dùng thành Người dùng đơn và điều này cuối cùng đã ngăn tôi xuất bản cơ sở dữ liệu.

Để khắc phục sự cố này, tôi đã phải đóng tất cả các phiên bản Visual Studio và chạy lệnh bên dưới trong cửa sổ truy vấn Sql Server -

USE [Your_Database_Name]; ALTER DATABASE [Your_Database_Name] SET MULTI_USER GO

Lệnh này đã thay đổi DB từ Người dùng đơn thành Người dùng Nhiều người và sau đó, tôi đã có thể xuất bản thành công.


1

Ngay cả tôi cũng gặp phải vấn đề tương tự, không thể tìm thấy các kết nối hoạt động với my_db để giết nó nhưng vẫn hiển thị lỗi tương tự. Tôi kết thúc việc ngắt kết nối tất cả các kết nối SSMS có thể cho bất kỳ cơ sở dữ liệu nào trên Máy chủ, tạo kết nối mới từ SSMS và thay đổi nó thành Nhiều người dùng.

-- Actual Code to change my_db to multi user mode
USE MASTER;
GO
ALTER DATABASE [my_db] SET MULTI_USER

Lưu ý: Đây có vẻ là một lỗi có thể có trong SQL Server 2005!


1

Chúng tôi vừa trải nghiệm điều này trong SQL 2012. Một quy trình sao chép đã nhảy vào khi chúng tôi giết phiên ban đầu đặt nó thành một người dùng. Nhưng sp_who2 không cho thấy quá trình mới được gắn vào DB. Đóng SSMS và mở lại sau đó cho phép chúng tôi xem quy trình này trên cơ sở dữ liệu và sau đó chúng tôi có thể tắt nó và chuyển sang chế độ multi_user ngay lập tức và điều đó đã hoạt động.

Tôi không thể tìm ra logic đằng sau điều này, nhưng nó dường như là một lỗi trong SSMS và vẫn đang tự thể hiện trong SQL 2012.


0

sử dụng tổng thể

ĐI

chọn d.name, d.dbid, spid, login_time, nt_domain, nt_username, loginame từ sys Processes p bên trong sysdatabase d trên p.dbid = d.dbid trong đó d.name = 'tên cơ sở dữ liệu'

giết 568 - giết spid

THAY ĐỔI tên cơ sở dữ liệu '

THIẾT LẬP MULTI_USER đi

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.