Как мне переименовать многие хранимые процедуры, не ломая вещи? - PullRequest
14 голосов
/ 22 июля 2010

В моей базе данных за несколько лет было несколько подрядчиков, и любые правила присвоения имен, которые могли когда-то существовать, были проигнорированы.

Я бы хотел переименовать хранимые процедуры в согласованный формат. Очевидно, что я могу переименовать их из SQL Server Management Studio, но это не будет обновлять вызовы, сделанные в коде сайта (C # / ASP.NET).

Могу ли я что-нибудь сделать, чтобы все вызовы были обновлены до новых имен, кроме поиска каждого старого имени процедуры в коде? Есть ли в Visual Studio возможность рефакторинга таких имен хранимых процедур?

NB. Я не считаю, что мой вопрос является дубликатом этого вопроса , поскольку последний вопрос касается исключительно переименования в базе данных.

Ответы [ 13 ]

39 голосов
/ 22 июля 2010

Вы можете внести изменения поэтапно:

  1. Копировать хранимые процедуры в новые хранимые процедуры под новым именем.
  2. Измените старые хранимые процедуры для вызова новых.
  3. Добавьте запись в старые хранимые процедуры, когда вы изменили весь код на сайте.
  4. Через некоторое время, когда вы не видите никаких вызовов старых хранимых процедур, и вы счастливы, что нашли все вызовы на веб-сайте, вы можете удалить старые хранимые процедуры и ведение журнала.
5 голосов
/ 22 июля 2010

Вы можете переместить «внутренности» SPROC в новый SPROC, соответствующий вашим новым соглашениям об именах, а затем оставить исходный sproc в качестве оболочки / оболочки, делегирующей новому SPROC.Вы также можете добавить таблицу аудита для отслеживания, когда вызывается старая оболочка SPROC - таким образом, вы будете знать, что нет никаких зависимостей от старого SPROC, и старый SPROC можно безопасно удалить (также убедитесь, что он неэто не просто «ваше приложение», использующее БД - например, кросс-объединения баз данных или другие приложения)

Это приводит к небольшому снижению производительности и не будет стоить вам так много (кроме возможности «найти»)ваши новые SPROCs легче)

3 голосов
/ 22 июля 2010

Вам нужно будет обработать это как минимум в двух областях: приложение и база данных.Могут быть и другие области, и вы должны быть осторожны, чтобы не пропустить их.

Заявка

Хорошая практика для будущих проектов

Помогает абстрагироваться от ваших звезд.В наших приложениях мы заключаем все наши sprocs в гигантский класс, я могу делать вызовы так:

Dim SomeData as DataTable = Sprocs.sproc_GetSomeData(5)

Таким образом, конец кода приятен и инкапсулирован.Я могу зайти в Sprocs.sproc_GetSomeData и настроить имя sproc только в одном месте, и, конечно, я могу щелкнуть правой кнопкой мыши по методу и сделать символическое переименование, чтобы исправить вызов метода для всего решения.

Без абстракции

Без этой абстракции вы можете просто найти Find In Files (Cntl + Shift + F) для имени sproc, а затем, если результаты выглядят правильно, откройте файлы и найдите / заменитевсе происшествия.

Сервер Sql

Не доверяйте зависимостям представлений

На стороне сервера SQL, теоретически в MSSMS 2008 выможно щелкнуть правой кнопкой мыши по sproc и выбрать View Dependencies.Это должно показать вам список всех мест, где sproc используется в базе данных, однако моя уверенность в этой функции очень низка.Может быть, лучше в SQL 2008, но в предыдущих версиях он определенно имел проблемы.

Просмотр зависимостей причиняет мне боль, и потребуется время, чтобы это исцелилось.:)

Wrap It!

В конечном итоге вам придется некоторое время держать старого спрока вокруг.Это главная причина, по которой переименование sprocs является таким проектом - для его завершения может потребоваться месяц.

Сначала замените его содержимое на некоторый простой TSQL, который вызывает новый sproc с теми же параметрами.и запишите некоторые записи, чтобы через некоторое время вы могли определить, действительно ли старый sproc не используется.

Наконец, когда вы уверены, что старый sproc не используется, удалите его.

Другие области?

Там может быть много другихобласти также.Службы отчетности приходят на ум.Пакеты служб SSIS.Использование техники сохранения старого спрока и перенаправления на новое (упомянутое выше) поможет вам узнать, пропустили ли вы что-нибудь, однако не сообщит вам , что вы пропустили.Это может привести к большой боли!

Удачи!

2 голосов
/ 22 июля 2010

Боюсь, это будет немного утомительный поиск по вашему исходному коду и другим объектам базы данных.

Не забудьте пакеты служб SSIS, задания агента SQL, rdl служб Reporting Services, а также код вашего основного приложения.

Вы можете использовать регулярное выражение, такое как spProc1|spProc2, чтобы искать в исходном коде все имена объектов одновременно, если у вас есть инструмент, который поддерживает поиск по файлам с помощью регулярных выражений (я использовал RegexBuddy для этого в прошлом )

Если вы хотите просто скрыть возможность того, что вы могли пропустить нечетную, вы можете оставить все предыдущие хранимые процедуры на месяц и просто зарегистрировать их пользовательское событие трассировки SQL с APP_NAME(), SUSER_NAME() и любую другую информацию, которую вы найдете полезной, затем попросите ее назвать переименованную версию. Затем настройте трассировку, отслеживающую это событие.

2 голосов
/ 22 июля 2010

Что касается изменения вашего приложения, у меня все мои сохраненные процы в качестве настроек в файле web.config, поэтому все имена находятся в одном месте и могут быть изменены в любое время в соответствии с изменениями в базе данных.

Когда приложению необходимо вызвать сохраненный процесс, имя определяется из web.config.

Это упрощает управление всеми потенциальными вызовами, которые приложение может выполнить на уровне служб баз данных.

2 голосов
/ 22 июля 2010

За исключением тестирования каждого пути в вашем приложении, чтобы убедиться, что все обращения к базе данных и соответствующие хранимые процедуры были обновлены ... нет.

Используйте глобальный поиск и замену (но просмотрите каждую предложенную замену), чтобы попытаться не пропустить ни одного экземпляра. Если ваше приложение хорошо структурировано, то на самом деле должно быть только 1 место для каждого хранимого процесса.

1 голос
/ 22 июля 2010
  1. Я получил бы список ссылок на процедуру, используя следующее, потому что зависимости SSMS не выбирают динамические ссылки SQL или ссылки вне базы данных.

    SELECT OBJECT_NAME(m.object_id), m.*
      FROM SYS.SQL_MODULES m
     WHERE m.definition LIKE N'%my_sproc_name%'
    
    • SQL нужно запускать в каждой базе данных, где могут быть ссылки.
    • syscomments и INFORMATION_SCHEMA.routines имеют столбцы nvarchar (4000). Так что, если «mySprocName» используется в позиции 3998, он не будет найден. syscomments имеет несколько строк, но ROUTINES усекается. Если вы не согласны, возьмите это с gbn .
  2. На основе этого списка зависимостей я бы создал новые хранимые процедуры, запускающие базовые хранимые процедуры - процедуры с наименьшим количеством зависимостей. Но я бы возражал , а не , чтобы создавать хранимые процедуры с префиксом имени "sp _"
  3. Убедитесь, что основные процедуры работают идентично существующим
  4. Перейти к следующему уровню хранимых процедур - повторять шаги 1-3 по мере необходимости, пока не будет обработана процедура самого высокого уровня.
  5. Проверьте переключение, которое приложение использует для новой процедуры - не ждите, пока все процедуры обновятся, чтобы проверить взаимодействие с кодом приложения. Это не нужно делать для каждой хранимой процедуры, но ожидание, чтобы сделать это оптом, тоже не лучший подход.

Параллельное развитие тоже имеет свои риски:

  • Любые изменения в существующем коде также должны применяться к новому коду. Если возможно, работайте в областях, где разработка заморожена, или используйте исправление ошибки в качестве возможности перехода на новый код, а не применяйте исправление в двух местах (при этом также минимизируется время простоя для перехода).
1 голос
/ 22 июля 2010

Я сделал это, и я в значительной степени полагался на глобальный поиск в моем исходном коде для имен хранимых процедур и копателя SQL, чтобы найти sql procs, который вызвал sql process.

http://www.sqldigger.com/

SQL Server (начиная с SQL 2000) плохо понимает свои собственные зависимости, поэтому остается искать текст сценариев, чтобы найти зависимости, которые могут быть другими хранимыми процессами или подстроками динамического sql.

1 голос
/ 22 июля 2010

Если вы используете соединение с БД, хранимыми процедурами и т. Д., Вы должны создать класс обслуживания для делегирования этих методов.

Таким образом, когда что-то в вашей базе данных, SP и т. Д. Изменяется, вам нужно только обновить класс обслуживания, и все защищено от взлома.

Существуют инструменты для VS, которые могут управлять изменением имени, например, refactor и resharper

0 голосов
/ 23 июля 2010

Предполагается, что вы используете SQL Server 2005 или выше. Вариант, который я использовал ранее, - переименовать старый объект базы данных и создать синоним SQL Server со старым именем. Это позволит вам обновлять ваши объекты в соответствии с любым выбранным соглашением и заменять ссылки в коде, пакетах служб SSIS и т. Д. По мере их поступления. Затем вы можете сосредоточиться на постепенном обновлении ссылок в вашем коде, независимо от того, какие версии обслуживания вы выберете (вместо того, чтобы ломать их все сразу). Поскольку вы чувствуете, что нашли все ссылки, вы можете удалить синоним, когда код переходит к QA.

...