I'm working with Delphi 7 and Firebird database. I'm using TIBDatabase, TIBTransaction, TIBQuery, TIBDataSet and DBGrid to establish connection and provide user interface for working with table. In my database I have two tables:
Ships
fields
Id integer
Name varchar(20)
Type_Id(Fk) integer
Longth integer
Ship_types
fields
Id(Pk) integer
Ship_type varchar(10)
So resulting dataset which I get through "join" query has such fields
Name
Type
Longth
Type is Ship_type field from Ship_types table joined via query by Type_Id foreign key to this table from Ships table.
Data is displaying properly.
Then I need to edit my data directly through DBGrid. For this purpose I use TIBUpdateSQL component. For displaying Type(lookup) field I chose DBGrid.Columns.PickList property.
So my question is how can I make TIBUpdateSQL work with such type of field? Cause I know that if it would be single table without foreign keys I have to write update statement into ModifySQL property of update component. But what have I do with fk fields? Can I write update join statement in UpdateSQL component or, if not, what else way I can do it?
I don't need to update two tables, I just need to update only Ships table but there is varchar(word representation) field in displaying dataset and in updating dataset it must be integer(corresponding id) to suit to table structure.
Editor in TIBUpdateSQL isn't solution for me cause I'm assigning query to TIBQuery on runtime.
You can't update tables using select with JOIN, only with subselects.
Sub-select example:
SELECT TABLE_NAME.*
, (SELECT TABLE_NAME2.NAME FROM TABLE_NAME2 WHERE TABLE_NAME2.ID = TABLE_NAME.ID)
FROM TABLE_NAME
Related
I have a DirectQuery table (Weather) which is sourced from an Azure SQL server. I would like to join this with an Imported table (Buckles) from an Excel sheet sourced from SharePoint Online.
Both tables have a UID field that is made up of a concatenation between a SiteID and timestamp. The UID field is named differently for each table.
I have created a One-To-Many relationship between the two tables.
I have tried to create a new DAX table using a NATURALINNERJOIN on Weather and Buckles but I get this error:
"No common join columns detected. The join function 'NATURALINNERJOIN' requires at-least one common join column."
I am confident it is not a problem with the underlying data because I've created a new imported Excel table (Test) with a selection of the data from Weather and I'm able to successfully create the join on Test and Buckles.
Is the joining of DirectQuery and Imported tables supported? I feel like this may be a type casting issue, but as far as I can see, both UID fields are set as Text.
The UID field is named differently for each table.
I suspect this may be the issue. NATURALINNERJOIN looks for matching column names
and if the two tables have no common column names, an error is returned.
Note that if you create a calculated DAX table using a DirectQuery source, I don't think that table will still act like DirectQuery. If I understand correctly, it will materialize the calculated table into your model and DAX that references that calculated table no longer points back to the SQL server (and consequently will only update when the calculated table gets rebuilt).
I am running a script to update a table structure, my problem is with the primary key column (id), the query creates a new id column each time I run my script.
This the first time that I am trying to write a script to update a database structure.
The database was created by an old version of an application,and now we want to release a new version of the application, but to achieve this goal I wrote a script which in summary is creating tables if they don't exist, adding columns to the tables if they don't exist, deleting old indexes and creating the new ones, etc.
The problem happens when the scripts add the primary key in the tables, in the database, the tables have a primary key column of type integer. But my query is not detecting this primary key column and it creates a new column with the same name and data type, at least that is what I see in PGAdmin v4.8.
Originally the primary key columns were created using the type serial and then PostgreSQL automatically creates a sequence and use it for the primary key.
How can I avoid the duplicated primary key columns?
Originally the column was created like follows
create table mytable(
id serial,
.
.
.
);
And if I look in the table, the column looks like this, which means that PostgreSQL created a sequence mytable_id_seq and used it for the auto increment value of primary key column.
id integer NOT NULL DEFAULT nextval('mytable_id_seq'::regclass)
But after I execute the following query and look in the table, it has a new column with the same name and data type like the one in the previous lines.
ALTER TABLE public.mytable ADD COLUMN IF NOT EXISTS id serial;
I am expecting to see only one column no matter how many times I execute the query.
I'm using database-first approach with Oracle. One of my table doesn't have a primary key. It only has 2 columns which are foreign keys of other tables.
I have generated model in ASP.NET MVC project from database (Add - New Item - ADO.NET Entity Data Model).
But there is a problem - I get an error:
Error 159: EntityType 'DbModel.Store.SomeTableWithoutPK' has no key defined. Define the key for this EntityType. E:\Git_repo\ZZ\ZZ.Domain\DAL\DbModel.edmx
Does this mean that each table must have a primary key? Can I avoid this? Or I will be forced to add new column with a primary key to this table? Of course there is also possibility to apply primary key to multiple column, but is it necessary?
Every table should have a primary key for database efficiency and so that you can edit records.
You don't need to create a new column for the primary key in your 2 column table
In designer, select both columns and use both together as the primary key. As long as nulls are not allowed and there are no duplicates you should be OK.
Since this is a many to many table and you are using EF, you may find later that adding a datetime column to the table with getdate() as the default value will make data maintenance easier
I have a DBGrid with a column based on a lookup field.
How can I set it up so that when a user clicks on the column title, it will sort by that field.
My problem here is that I can't figure out a way to create an index on a lookup field.
I'm using Absolute Database for this, but most things that work with the BDE or TClientDataSet will work with Absolute.
Thanks!
I don't think it is possible to create an index on a lookup field. It is possible to create an index on an internally calculated field of a ClientDataSet though. In the OnCalcFields event handler set its value to the value of the lookup field. And set the visible property of the lookup field to false. Now you can sort on the internally calculated field.
What you could do (especially if the data is readonly, and does not have zillions of rows) is use a ClientDataSet to display data in your grid.
Roughly the steps would be like this:
Load the data from your regular into the ClientDataSet,
add a calculated field to the ClientDataSet that contains the value obtained from the lookup,
then add an index to that calculated
field.
--jeroen
You cannot sort by a lookup field. But you can 'fake' this. Let's suppose that you have the following tables: (PK means Primary Key)
Contacts
ID - Integer (PK)
NAME - Varchar(40)
COUNTRYID - Integer
Countries
ID - Integer (PK)
NAME - Varchar(40)
Then you can have the following query in the dataset which is linked to the TDBGrid:
SELECT C.ID, C.NAME, C.COUNTRYID, CO.NAME
FROM CONTACTS C
JOIN COUNTRIES CO ON C.COUNTRYID=CO.ID
(Not tested but I think that you got the idea)
Also you can put this in a view.
Then you'll display in your TDBGrid (as columns) only the ID, NAME and the desired lookup field which you already have (let's call it COUNTRYLOOK).
When one clicks on the Title Header you can change the query by adding in the 4th line an ORDER BY . For the specific column of the lookup field (COUNTRYLOOK), instead of using the 1:1 mapping you can put in the 4th line of your query ORDER BY CO.NAME. Reopen the query and that's it. In practice is much more simpler than my description here.
DevExpress ExpressQuantumGrid can do it, check it out:
http://www.devexpress.com/products/vcl/exquantumgrid/
Now I have seen this question in another forum but it didn't had an acceptable answer.
Suppose I have two tables, the Groups table and the Elements table. The tables have no defined relationships. The Elements table has an IdGroup field that refers to the IdGroup (PK) field of the Groups table.
I use the following query through an ADO recordset to populate the tables values to a datagrid:
SELECT Elements.*, Groups.GroupName
FROM Elements
INNER JOIN Groups ON Elements.IdGroup = Groups.IdGroup
From that grid I want to press Delete in order to delete an Element. Here is my problem. When I used DAO, the DAO Delete() function deleted only the record in the Elements group. This was the expected behavior.
When I changed to ADO, the Delete() function deleted records in both tables, the element record and the group to which the element belonged!
Is there any way to reproduce the DAO behavior in ADO without having to define relationships into the tables?
Note: I know there are alternatives (executing DELETE querys could do the job). Just show me a way to do this in ADO, or say it cannot be done.
Rewrite you query to:
replace the INNER JOIN with a WHERE clause consisting of an EXISTS;
use a subquery in the SELECT clause to return the value of Groups.GroupName.
Example:
SELECT Elements.*,
(
SELECT Groups.GroupName
FROM Groups
WHERE Elements.IdGroup = Groups.IdGroup
)
FROM Elements
WHERE EXISTS (
SELECT *
FROM Groups
WHERE Elements.IdGroup = Groups.IdGroup
);
I've tested this using SQL Server 2008 with a ADO recordset set as the DataSource property of a Microsoft OLEDB Datagrid Control (MSDATGRD.OCX) then deleting the row via the gird (I assume you are doing something similar) and the row is indeed deleted from table Elements only (i.e. the row in Groups remains undeleted).
Note the revised query may have a negative impact on performance when fetching rows.