Dynamiczne zapytanie tableadaptera

0

Witam,

Bawię się trochę C# i nawet pare narzędzi udało mi się zrobić mam jednak problem z bazą Ooracle a raczej z C#. Problem polega na tym, iż chce robić dynamiczne query do table adaptera np FillbyWhere, który doklejałby warunek where zbudowany na podstawie jakiegoś formularza zapytania. Próbowałem dodać query FillByWhere i zaraz bo selcie w sekcj iwhere umieszczalem parametr ale to nie daje efektu bo przy zapytaniu sypie się błędami z bazy. Być może jednak lepiej byłoby wpływać na zawartość kolekcj iw table adapterze bo jest tam partial... Proszę o podpowiedź jak przekazać dynamiczny warunek where to znaczy taki , który jest uzależniony od wypełnionych warunków w formularzu ponadto chcę zrobić obsługę (=, !=, like, in, not in).

0

Myślę, że jak napiszesz to po polsku i dasz przykładowy kod, który Ci nie działa to ktoś może się nawet pokusić o odpowiedź

0

A więc tak.
Pierwsze co próbuje robić to dodać do tableAdaptera query poprzez wizarda w Visual Studio 2012. Wymyśliłem to sobie tak ze dodam query FillByWhere(p_where).
Zapytanie:

SELECT "ID", "FIRMA", "NR_PRAC", "NAZW_IMIE", "ID_OSOBY", "AKTYWNY"  FROM "SCHEMAT"."V_PRAC"
WHERE p_where 

Gdzie p_where to właśnie parametr w którym chciałbym przekazywać mój dynamicznie stworzony warunek na podstawie wypełnionych pól w formularzu.
Przy zapisie takiego zapytania Visual Studio rzuca się że warunek where jest nieprawidłowy. Olewam ten komunikat idę dalej dodaje parametr do kolekcji parametrów zapytania o nazwie p_where. Następnie próbuje wyświetlić dane poprzez preview data gdzie uzupełniam parametr np.: FIRMA = 'COS' no i to nie działa Oracle zwraca błąd: ORA-00920: invalid relational operator (czyli moje zapytanie nie wygląda tak jakbym tego chciał).

Idąc dalej to widzę że klasa tableAdaptera posiada kolekcję:

         private void InitCommandCollection() {
            this._commandCollection = new global::System.Data.OleDb.OleDbCommand[1];
            this._commandCollection[0] = new global::System.Data.OleDb.OleDbCommand();
            this._commandCollection[0].Connection = this.Connection;
            this._commandCollection[0].CommandText = "SELECT \"ID\", \"FIRMA\", \"NR_PRAC\", \"NAZW_IMIE\", \"ID_OSOBY\", \"AKTYWNY\" +
               FROM \"SCHEMAT\".\"V_PRAC\"";
            this._commandCollection[0].CommandType = global::System.Data.CommandType.Text;
        }

Czy istnieje sposób aby w locie podmieniać wartość CommandText? Wtedy po kliknięciu OK w formularzu zapytania podmieniałbym ten wpis w kolekcji i został by mi zwrócony odpowiedni wynik.

To co chcę uzyskać to możliwość przekazywania warunku na podstawie danych z formularza.

0
  1. gdzie dodajesz ten parametr bo w kodzie tego nie widzę
  2. o ile dobrze rozumiem to próbujesz jako parametr przekazać cały warunek a to nie tak działa - możesz zrobić tak WHERE id = ? AND nazwa = ? i to właśnie te ? to są parametry, które następnie trzeba uzupełnić
  3. to co chcesz zrobić można osiągnąć tak: this._commandCollection[0].CommandText = "SELECT ... FROM ... WHERE " + pWhere
0

Odp.3.
Jak stringa złączyć to wiem :)

Inaczej chciałbym uzyskać coś podobnego do tego:
http://www.codeproject.com/Articles/17324/Extending-TableAdapters-for-Dynamic-SQL

Choć jest to w VB chciałbym to przerobić na C# bo to dokładnie to o co mi chodzi.

0

no ale tam jest przecież dokładnie tak jak w moim poście wyżej - Me._commandCollection(0).CommandText += " WHERE " + WhereExp
Nadal nie mam pojęcia z czym masz problem

0

Ok spróbuję z tym powalczyć dzisiaj.

Jeszcze jedno pytanie czy to query na tableAdapterze może działać tak, że są np. parametry i jeśli w formularzu w textboxie użytkownik nic nie wpisze to ten parametr jest pomijany?
Inaczej bazując na tych zapytaniach z wizzarda musiałbym ich stworzyć tyle ile jest możliwych kombinacji dla pól.

Ps. Dzięki za pomoc.

0

nie. Takie coś robi się jak już to tak

select * from tabela where (@param1 is null or @param1 = kolumna1) and (@param2 is null or @param2 = kolumna2)

trzeba jednak dodać wszystkie parametry natomiast tym, które nie mają wartości trzeba ustawić wartość na DBNull

0

Dzięki wielkie za pomoc. Faktycznie było to proste jak sikanie ja nie wiedziałem tylko jak ten parametr przekazywać ale sobie porawdziłem.

0

Zrobiłem to jednak jak odświeżać zapytanie z tableAdaptera?
Utworzyłem na formie MenuStrip z textboxami na parametry oraz dwa przyciski jeden filtruj drugi pobierz wszystko. Wszystko działa dobrze za pierwszym razem tzn. przy pierwszym naciśnięciu przycisku i potem jakby zapytanie jest utrwalone. Klikanie w przyciski nie zmienia danych w DataTable. Poniżej część kodu:

 using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;

namespace WindowsFormsApplication1.SubFormatkiMDI.SynchronizacjaPracownicy
{
    public partial class SynchronizacjaPracownicy : Form
    {
        private string l_warunekWhere;

        public SynchronizacjaPracownicy()
        {
            InitializeComponent();
        }

        private void SynchronizacjaPracownicy_Load(object sender, EventArgs e)
        {

            l_warunekWhere = null;
			
            this.v_SYNC_PRACTableAdapter.setWarunekWhere(l_warunekWhere);
            this.v_SYNC_PRACTableAdapter.Fill(this.dataSetNrz1.V_SYNC_PRAC);
        }


        private void SynchronizacjaPracownicy_LoadZWarunkiem(object sender, EventArgs e)
        {

            l_warunekWhere = null;

            // pobierz dane z formularza
            if (!String.IsNullOrEmpty(toolStripTextBoxFirma.Text))
            {
                l_warunekWhere = l_warunekWhere + " FIRMA = '" + toolStripTextBoxFirma.Text + "'";
            }
            if (!String.IsNullOrEmpty(toolStripTextBoxIdOsoby.Text))
            {
                l_warunekWhere = l_warunekWhere + " AND ID_OSOBY = '" + toolStripTextBoxIdOsoby.Text + "'";
            }
            if (!String.IsNullOrEmpty(toolStripTextBoxNazwiskoImie.Text))
            {
                l_warunekWhere = l_warunekWhere + " AND NAZW_IMIE = '" + toolStripTextBoxIdOsoby.Text + "'";
            }

            if (!String.IsNullOrEmpty(l_warunekWhere))
            {
                l_warunekWhere = " WHERE" + l_warunekWhere;
            }
            
            this.v_SYNC_PRACTableAdapter.setWarunekWhere(l_warunekWhere);
            
            try
            {
                this.v_SYNC_PRACTableAdapter.Fill(this.dataSetNrz1.V_SYNC_PRAC);
            }
            catch (System.Exception ex)
            {
                System.Windows.Forms.MessageBox.Show(ex.Message);
            }
           
        }       
    }
}

Po zmianie wartości w textboxach dalej zwracane są wyniki z pierwszego zapytania jak to odświeżyć?

0

Ok już sam to rozwiązałem dodałem w metodzie tableadaptera InitCommandCollection(); po ustawieniu zmiennej z warunkiem:

 public void setWarunekWhere(string p_where)
        {
            l_warunek = p_where;
            InitCommandCollection();
        } 

I to rozwiązuje problem.

1 użytkowników online, w tym zalogowanych: 0, gości: 1