KevinClaassens Ответов: 4

Как вернуть конкретное значение из базы данных


У меня есть две метки на моей странице, которые нужно изменить в соответствии с тем, какой пользователь вошел в систему.

Сначала я хочу получить имя дисциплины из базы данных. В моей базе данных есть таблица ATHLETE_MEETING_DISCIPLINE_RESULT, которая ссылается на спортсмена и MEETING_EVENTS.

Таблица MEETING_EVENTS - это связующая таблица для собраний и дисциплины.

Адрес электронной почты находится в таблице USER, которая также ссылается на таблицу ATHLETE_MEETING_DISCIPLINE_RESULT

Я использую 3-уровневый метод.

этот метод находится на уровне доступа к данным, где я пытался вернуть имя дисциплины с помощью хранимой процедуры.

public string GetAthleteDiscipline(string email)
        {
            string disciplineName = null;
            string connString = ConfigurationManager.ConnectionStrings["dbConnection"].ConnectionString;
            //SqlConnection con = new SqlConnection(connString);
            try
            {
                //con.Open();
                using (SqlConnection con = new SqlConnection(CS))
                {
                    SqlCommand cmd = con.CreateCommand();
                    cmd.CommandType = CommandType.StoredProcedure;
                    cmd.CommandText = "spGetAthleteDiscipline";
                    disciplineName = cmd.ExecuteNonQuery().ToString();
                }
            }
            catch (Exception)
            {

            }
            return disciplineName;
        }


В моем слое бизнес-логики у меня есть

public string GetAthleteDiscipline(string emailAddress)
        {
            return db.GetAthleteDiscipline(emailAddress);
        }



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

lblDisciplineID.Text = bll.GetAthleteDiscipline(email)


Что я уже пробовал:

моя хранимая процедура выглядит следующим образом:

Выберите имя Д.,AMDR.FinishingResult,AMDR.Размещение
Из дисциплины как D, [пользователь] как U, MEETING_EVENTS как ME, ATHLETE_MEETING_DISCIPLINE_RESULT как AMDR
Где U. EmailAddress = @emailAddress
И AMDR. MeetingDisciplineID = ME.MeetingDisciplineID
И я.DisciplineID = D. DisciplineID.

но значение dicipline, которое я пытаюсь получить, всегда равно null или пусто

4 Ответов

Рейтинг:
29

OriginalGriff

Попробуйте присоединиться - я не могу быть конкретным, не зная схемы таблицы и отношений столбцов, но если у вас есть две таблицы пользователей и адресов

Users      (ID, Name)
Addresses  (ID, UserID, Address)

Затем
SELECT u.Name, a.Address
FROM Users u
JOIN Addresses a ON a.UserId = u.ID
Затем он возвращает каждое имя пользователя с соответствующим адресом - это похоже на то, что вы пытаетесь сделать со своим SP.

РЕДАКТИРОВАТЬ:

Хорошо - первое, что нужно заметить, это то, что у вас нет записей спортсменов!
У вас есть пользователи, но нет спортсменов.
Так что все, что вы попытаетесь использовать AthleteID, вызовет проблемы.
А Элвин Грин соревновался в беге на 100 метров и метании диска, а не в беге на 400 метров с барьерами:

SELECT * FROM ATHLETE_MEETING_DISCIPLINE_RESULT a
JOIN DISCIPLINE d ON a.MeetingDisciplineID = d.DisciplineID

SELECT * FROM ATHLETE_MEETING_DISCIPLINE_RESULT
SELECT * FROM DISCIPLINE 


Элвин-это ID 18, который является идентификаторами дисциплины 1 и 20.

Так что попробуйте это:
SELECT u.FirstName, u.LastName, d.Name, AMDR.FinishingResult, AMDR.Placement FROM ATHLETE_MEETING_DISCIPLINE_RESULT AMDR 
JOIN [USER] u ON AMDR.AthleteID = u.UserID
JOIN MEETING_EVENTS ME ON me.MeetingDisciplineID = AMDR.MeetingDisciplineID
JOIN DISCIPLINE d ON d.DisciplineID = AMDR.MeetingDisciplineID
WHERE U.EmailAddress = @emailAddress


Что дает
FirstName LastName  Name          FinishingResult Placement
Alvin     Green     100m          12.09           4
Alvin     Green     Discuss Throw 57.4            3


KevinClaassens

Я хочу вернуть имя dicipline. Поскольку я использую электронную почту в качестве первичного ключа, я подумал, что смогу использовать ее. У меня есть таблица пользователей, и в этой таблице у меня есть адреса электронной почты пользователей. Могу ли я выслать вам изображение схемы базы данных? Мне трудно объяснить, с чем именно я борюсь. Но я думаю, что это хранимая процедура

OriginalGriff

Не используйте электронную почту в качестве первичного ключа - люди время от времени меняют адреса электронной почты, и это становится очень сложным, когда они это делают. Вместо этого используйте значение идентификатора автоматического приращения и используйте его в качестве "поля связывания" - это также экономит чертовски много места в БД.
Никогда не отправляйте фотографии: вместо этого скопируйте и вставьте свою схему. Таким образом, если людям нужно что - то проверить, им не нужно печатать-помогите нам помочь вам!

KevinClaassens

Это может быть очень глупый вопрос, но как мне скопировать и вставить схему?

OriginalGriff

Откройте БД в SSMS, откройте ветвь таблиц и щелкните правой кнопкой мыши имя таблицы.
В контекстном меню выберите пункт " таблица сценариев как ... создать в ... буфер обмена"
Затем вставьте определение туда, где оно вам нужно.

KevinClaassens

Используйте [XcellIT]
ГО

/ * * * * * * Объект: таблица [dbo].[ATHLETE_MEETING_DISCIPLINE_RESULT] Дата сценария: 2016/09/08 12: 20: 32 PM ******/
УСТАНОВИТЕ ANSI_NULLS ON
ГО

УСТАНОВИТЕ QUOTED_IDENTIFIER НА
ГО

Создайте таблицу [dbo].[ATHLETE_MEETING_DISCIPLINE_RESULT](
[AthleteMeetingDisciplineID] [int] IDENTITY(1,1) NOT NULL,
[AthleteID] [int] NULL,
[MeetingDisciplineID] [int] NULL,
[FinishingResult] [float] NULL,
[Размещение] [int] NULL,
Ограничение [PK_amr] первичный ключ КЛАСТЕРИЗОВАН
(
[AthleteMeetingDisciplineID] ASC
)С (КАК = ВЫКЛ, STATISTICS_NORECOMPUTE = OFF, ТО ЗНАЧЕНИЕ IGNORE_DUP_KEY = OFF, ТО ПАРАМЕТРЫ ALLOW_ROW_LOCKS = ON, ТО ALLOW_PAGE_LOCKS ИНСТРУКЦИИ =) НА [ОСНОВНОЙ]
) НА [ПЕРВИЧНОМ]

ГО


Используйте [XcellIT]
ГО

/ * * * * * * Объект: таблица [dbo].[MEETING_EVENTS] Дата сценария: 2016/09/08 12:21: 07 PM ******/
УСТАНОВИТЕ ANSI_NULLS ON
ГО

УСТАНОВИТЕ QUOTED_IDENTIFIER НА
ГО

Создайте таблицу [dbo].[MEETING_EVENTS](
[MeetingDisciplineID] [int] IDENTITY(1,1) NOT NULL,
[Идентификатором собрания] [инт] нуль,
[DisciplineID] [int] NULL,
[DateTime] [smalldatetime] NULL,
[ConditionID] [int] NULL,
ОГРАНИЧЕНИЕ [PK_MEETING_EVENTS] ПЕРВИЧНЫЙ КЛЮЧ КЛАСТЕРИЗОВАН
(
[MeetingDisciplineID] ASC
)С (КАК = ВЫКЛ, STATISTICS_NORECOMPUTE = OFF, ТО ЗНАЧЕНИЕ IGNORE_DUP_KEY = OFF, ТО ПАРАМЕТРЫ ALLOW_ROW_LOCKS = ON, ТО ALLOW_PAGE_LOCKS ИНСТРУКЦИИ =) НА [ОСНОВНОЙ]
) НА [ПЕРВИЧНОМ]

ГО

Используйте [XcellIT]
ГО

/ * * * * * * Объект: таблица [dbo].[Дисциплина] дата сценария: 2016/09/08 12: 21: 26 PM ******/
УСТАНОВИТЕ ANSI_NULLS ON
ГО

УСТАНОВИТЕ QUOTED_IDENTIFIER НА
ГО

УСТАНОВИТЬ ПАРАМЕТР ANSI_PADDING НА
ГО

Создайте таблицу [dbo].[ДИСЦИПЛИНА](
[DisciplineID] [int] IDENTITY(1,1) NOT NULL,
[Имя] [varchar] (50) NULL,
[Описание] [varchar] (50) NULL,
[DisciplineType] [varchar] (50) NULL,
ОГРАНИЧЕНИЕ [PK_DISCIPLINE1] ПЕРВИЧНЫЙ КЛЮЧ КЛАСТЕРИЗОВАН
(
[DisciplineID] ASC
)С (КАК = ВЫКЛ, STATISTICS_NORECOMPUTE = OFF, ТО ЗНАЧЕНИЕ IGNORE_DUP_KEY = OFF, ТО ПАРАМЕТРЫ ALLOW_ROW_LOCKS = ON, ТО ALLOW_PAGE_LOCKS ИНСТРУКЦИИ =) НА [ОСНОВНОЙ]
) НА [ПЕРВИЧНОМ]

ГО

НАБОР ВЫБРАНО ЗНАЧЕНИЕ ВЫКЛ.
ГО


Используйте [XcellIT]
ГО

/ * * * * * * Объект: таблица [dbo].[ВСТРЕЧА] Дата сценария: 2016/09/08 12:22: 07 PM ******/
УСТАНОВИТЕ ANSI_NULLS ON
ГО

УСТАНОВИТЕ QUOTED_IDENTIFIER НА
ГО

УСТАНОВИТЬ ПАРАМЕТР ANSI_PADDING НА
ГО

Создайте таблицу [dbo].[ВСТРЕЧА](
[MeetingID] [int] IDENTITY(1,1) NOT NULL,
[VenueID] [int] NOT NULL,
[MeetingName] [varchar] (50) NULL,
[MeetingStart] [дата] NULL,
[MeetingEnd] [дата] NULL,
ОГРАНИЧЕНИЕ [PK_MEETING1] ПЕРВИЧНЫЙ КЛЮЧ КЛАСТЕРИЗОВАН
(
[Идентификатором собрания] АСК
)С (КАК = ВЫКЛ, STATISTICS_NORECOMPUTE = OFF, ТО ЗНАЧЕНИЕ IGNORE_DUP_KEY = OFF, ТО ПАРАМЕТРЫ ALLOW_ROW_LOCKS = ON, ТО ALLOW_PAGE_LOCKS ИНСТРУКЦИИ =) НА [ОСНОВНОЙ]
) НА [ПЕРВИЧНОМ]

ГО

НАБОР ВЫБРАНО ЗНАЧЕНИЕ ВЫКЛ.
ГО


Используйте [XcellIT]
ГО

/ * * * * * * Объект: таблица [dbo].[ПОЛЬЗОВАТЕЛЬ] Дата сценария: 2016/09/08 12:25: 13 PM ******/
УСТАНОВИТЕ ANSI_NULLS ON
ГО

УСТАНОВИТЕ QUOTED_IDENTIFIER НА
ГО

УСТАНОВИТЬ ПАРАМЕТР ANSI_PADDING НА
ГО

Создайте таблицу [dbo].[ПОЛЬЗОВАТЕЛЬ](
[UserID] [int] IDENTITY(1,1) NOT NULL,
[FirstName] [varchar] (50) NULL,
[Фамилия] [varchar] (50) NULL,
[DateOfBirth] [date] NULL,
[Пол] [varchar] (50) NULL,
[Адрес электронной почты] [varchar] (50) NULL,
[Пароль] [varchar] (50) NULL,
[Город] [варчар] (50) ноль,
[PhoneNumber] [varchar] (50) NULL,
[ClubID] [int] NOT NULL,
[UserType] [varchar](50) NOT NULL,
ОГРАНИЧЕНИЕ [PK_USER1_1] ПЕРВИЧНЫЙ КЛЮЧ КЛАСТЕРИЗОВАН
(
[Имя пользователя] АСК
)С (КАК = ВЫКЛ, STATISTICS_NORECOMPUTE = OFF, ТО ЗНАЧЕНИЕ IGNORE_DUP_KEY = OFF, ТО ПАРАМЕТРЫ ALLOW_ROW_LOCKS = ON, ТО ALLOW_PAGE_LOCKS ИНСТРУКЦИИ =) НА [ОСНОВНОЙ]
) НА [ПЕРВИЧНОМ]

ГО

НАБОР ВЫБРАНО ЗНАЧЕНИЕ ВЫКЛ.
ГО

Используйте [XcellIT]
ГО

/ * * * * * * Объект: таблица [dbo].[Спортсмен] дата сценария: 2016/09/08 12: 27: 40 PM ******/
УСТАНОВИТЕ ANSI_NULLS ON
ГО

УСТАНОВИТЕ QUOTED_IDENTIFIER НА
ГО

УСТАНОВИТЬ ПАРАМЕТР ANSI_PADDING НА
ГО

Создайте таблицу [dbo].[СПОРТСМЕН](
[AthleteID] [int] IDENTITY(1,1) NOT NULL,
[FirstName] [varchar] (50) NULL,
[Фамилия] [varchar] (50) NULL,
[Пол] [varchar] (50) NULL,
[DOB] [smalldatetime] NULL,
ОГРАНИЧЕНИЕ [PK_ATHLETE1] ПЕРВИЧНЫЙ КЛЮЧ КЛАСТЕРИЗОВАН
(
[AthleteID] ASC
)С (КАК = ВЫКЛ, STATISTICS_NORECOMPUTE = OFF, ТО ЗНАЧЕНИЕ IGNORE_DUP_KEY = OFF, ТО ПАРАМЕТРЫ ALLOW_ROW_LOCKS = ON, ТО ALLOW_PAGE_LOCKS ИНСТРУКЦИИ =) НА [ОСНОВНОЙ]
) НА [ПЕРВИЧНОМ]

ГО

НАБОР ВЫБРАНО ЗНАЧЕНИЕ ВЫКЛ.
ГО

Я сделал все так, как ты мне велел. Я просто скопировал и вставил все разные сценарии

OriginalGriff

Хорошо - я только что скопировал это, и у меня есть копия вашей базы данных (без данных) - видите, насколько это проще? :смеяться:
Первое, что я замечаю, это то, что вы не устанавливаете никаких отношений с внешними ключами - и, вероятно, должны это сделать, чтобы SQL мог обеспечить реляционную целостность.
И вы, похоже, нигде не ссылаетесь на свою таблицу пользователей, что, вероятно, является ошибкой - поскольку я предполагаю, что спортсмен и пользователь каким-то образом связаны?
Итак, то, что вы хотите, - это ученик.Имя и некоторые детали из таблицы ATHLETE_MEETING_DISCIPLINE_RESULT, основанные на адресе электронной почты (который должен исходить из таблицы USER) - это, вероятно, довольно простое соединение, но в вашей схеме нет ничего, что связывало бы пользователя с чем-либо еще!

KevinClaassens

Большое вам спасибо за ваше время! Это очень ценится:). Таблица спортсменов будет содержать все данные о спортсменах, независимо от того, зарегистрированы они или нет, а таблица пользователей-для зарегистрированных пользователей. Я тоже модифицированный хранимой процедурой теперь выгляжу так

Выберите имя Д.
Из дисциплины как D, [пользователь] как U, MEETING_EVENTS как ME, ATHLETE_MEETING_DISCIPLINE_RESULT как AMDR
Где U. EmailAddress = @emailAddress
И AMDR. MeetingDisciplineID = ME.MeetingDisciplineID
И я.DisciplineID = D. DisciplineID
И U. UserID = AMDR.Спортсмен

В SSMS он возвращает правильный результат сейчас,но в моем коде дисциплина все еще возвращает null

OriginalGriff

Значит, AthleteID и UserID - это одно и то же?
В этом случае вы дублируете поля firstname, LastName, Gender и DOB - у меня будет другой идентификатор пользователя (и уникальный для таблицы USER), и замените эти четыре поля на AthleteID.
А пока рассмотрим использование соединения для объединения таблиц в одну строку:

Выберите D.Имя, AMDR.FinishingResult,AMDR.Размещение
Из дисциплины d
Присоединяйтесь ATHLETE_MEETING_DISCIPLINE_RESULT AMDR на D.DisciplineID = AMDR.MeetingDisciplineID
ПРИСОЕДИНЯЙТЕСЬ MEETING_EVENTS МЕНЯ.DisciplineID = д.DisciplineID
Присоединяйтесь к спортсмену а на а.AthleteID = AMDR.Спортсмен
Присоединяйтесь к [пользователь] у-у.Идентификатор пользователя = а.AthleteID
Где U. EmailAddress = @emailAddress

Попробуйте сделать это в SSMS, и вы получите одну строку с нужными данными.

KevinClaassens

он ничего не возвращает:(

OriginalGriff

ОК. Есть ли у вас простой образец данных, который должен возвращать то, что вы хотите?
Это должна быть вся связанная информация о таблице.

KevinClaassens

Когда я ввожу адрес электронной почты ex. s214311848@nmmu.ac.za он должен вернуть 100-метровые и 400-метровые барьеры. Это то, что ты хочешь знать?

OriginalGriff

Ну да, но мне нужны исходные данные для того пользователя, который генерирует результат.
Это данные для всех 6 таблиц, так что я могу видеть, что запрос должен получить. (Вы можете запутать имена и электронные письма по соображениям защиты данных, если это "реальные" данные).

Затем я подключу это к схемам таблиц, которые вы дали, и проверю запросы, чтобы получить "правильный" результат. Есть смысл?

KevinClaassens

В этом есть смысл. Для получения части данных. Должен ли я просто скопировать и вставить все? или есть какой-то способ сделать это в SSMS?

OriginalGriff

"Все" собирается сделать для большого поста!
Если вы используете SSMS, вы можете экспортировать его:
Щелкните правой кнопкой мыши имя базы данных и выберите пункт " задачи...созданный сценарий"
Это поднимает волшебника,который ведет вас.
В диалоговом окне" установить параметры сценариев "нажмите кнопку" Дополнительно " и измените "типы данных для сценария" на " схема и данные"
Это создаст текстовый файл, содержащий схему и инструкции INSERT, чтобы убедиться, что у нас есть одни и те же данные.
Загрузите его в Dropbox или что-то подобное и разместите ссылку.

KevinClaassens

Еще раз. Большое вам спасибо за ваше время и усилия, чтобы помочь мне:) https://www.dropbox.com/s/b97wsw2a2q4zgku/script.sql?dl=0

OriginalGriff

Ответ обновлен

Dave Kreskowiak

Сверх того, как обычно. А 5.

KevinClaassens

Большое вам спасибо за ваше время и усилия. Это очень ценится

OriginalGriff

Пожалуйста!

Рейтинг:
2

Wastedtalent

Вы пробовали добавить этот параметр в запрос?

cmd. Parameters ["@emailAddress"]. Value = email;


KevinClaassens

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

Рейтинг:
2

NaibedyaKar

Можете ли вы проверить, возвращает ли ваша хранимая процедура правильные значения, если она выполняется отдельно?

Я чувствую, что запрос на SP не является правильным. Связь между таблицей [USER] и ATHLETE_MEETING_DISCIPLINE_RESULT не предусмотрена. Можете ли вы проверить приведенный ниже сценарий?

SELECT * FROM DISCIPLINE d 
INNER JOIN MEETING_EVENTS me ON d.DisciplineID = me.DisciplineID
INNER JOIN ATHLETE_MEETING_DISCIPLINE_RESULT amdr ON me.MeetingDisciplineID = amdr.MeetingDisciplineID
INNER JOIN [USER] u ON u.UserId = amdr.UserId --This relation is missing
WHERE u.EmailAddress = @emailAddress --Put the email address here and see if it working then use it on the SP


KevinClaassens

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

дисциплина = bll.GetAthleteDiscipline(электронная почта);

Рейтинг:
1

F-ES Sitecore

ExecuteNonQuery означает выполнение запроса и игнорирование любых результатов, поскольку они вас не интересуют. Очевидно, что это не то, что вы хотите сделать, поскольку вы хотите получить результаты. ExecuteNonQuery должен использоваться для таких вещей, как вставка, обновление и удаление, которые не возвращают данные, а не для запросов SELECT.

Вместо использования метода executereader

Свойство sqlcommand.Метод ExecuteReader (System. Data.SqlClient)[^]


KevinClaassens

Теперь я изменил свой код, чтобы он выглядел так
public string GetAthleteDiscipline(строка электронной почты)
{
строки дисциплина = нулевой;
строка connString = ConfigurationManager.ConnectionStrings ["dbConnection"].Параметр connectionString;
SqlConnection con = new SqlConnection(connString);

пробовать
{

против.Открыть();
SqlCommand cmd = new SqlCommand ("spGetAthleteDiscipline");

использование (SqlDataReader reader = cmd.Метода executereader())
{
в то время как (читатель. читать())
{
дисциплина = (читатель ["имя"].Метод toString());
}
}
}
catch (исключение)
{

}
вернуть дисциплину;
}
но дисциплина все равно равна нулю

F-ES Sitecore

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

Если Дисциплина равна нулю, то строка ToString не выполнялась, так что, скорее всего, ваш запрос не возвращает никаких данных. Вы бы знали это, если бы прошли через код, так как цикл while будет пропущен. Вы не прикрепляете параметр emailAddress, поэтому ваш proc никогда не будет возвращать данные, и если вы прикрепляете его, и он все еще не работает, то нет данных, где u.EmailAddress удовлетворяет данным, которые вы передаете. Мы не можем получить доступ к вашей базе данных, поэтому мы не можем предположить, почему это так, скорее всего, данных просто нет, или ваши соединения таблиц неверны, только вы можете решить эти вещи.