QSqlField name() method returns "" - c++

I have a class (ServicesTableModel) which inherits from QSqlRelationalTableModel. In the constructor I have:
ServicesTableModel::ServicesTableModel( QWidget* parent, QSqlDatabase db )
: QSqlRelationalTableModel( parent, db )
{
setTable( "servicios" );
select();
...
}
Now, if I place the line
qDebug() << primaryKey();
where the dots are I get
QSqlRecord( 1 )
" 0:" QSqlField("ser_id", int, required: no, generated: yes)
which makes perfect sense, but after
qDebug() << primaryKey().name();
the answer is
""
so I can't reach the name of the primary key.
The table is sqlite, defined with
CREATE TABLE servicios (ser_id integer primary key, ... )
This matters because I'm trying to generalize the class for objects closely related to the rows in a table, and it seems natural not to have to provide the primary key name to the constructor.
I must surely be doing something wrong, or I don't understand what the name()_ method from QSqlField does.

primaryKey.name() returns the name of the index.
In SQL, an index can be named, and this is independent from the name of the field(s) used for the key.
An index can work on several fields.
Each field name can be retrieved with key.fieldName(i), with 0<i<key.count()

Related

Filtering Lookup for String x++

I had lookup fields (type:int64, Extended from RefRecId) and I had written lookup filtering code for them but I had to convert them into strings ( I had added relations to make them lookup fields) But since they are "String" instead of "reference group" my code doesn't work. How can I filter them when they are 'string'. Here is my code for filtering for reference groups:
[FormControlEventHandler(formControlStr(InventSite, InventSite_MyField), FormControlEventType::Lookup)]
public static void InventSite_MAndEDay_OnLookup(FormControl sender, FormControlEventArgs e)
{
SysReferenceTableLookup tableLookup = SysReferenceTableLookup::newParameters(tableNum(ReferenceTables), sender);
Query query = new Query();
InventSite inventSite;
QueryBuildDataSource qbds = query.addDataSource(tableNum(ReferenceTables));
qbds.addRange(fieldNum(ReferenceTables,ReferenceTablesType )).value(queryValue(ReferenceTablesTypeBaseEnum::MyField));
tableLookup.addLookupField(fieldNum(ReferenceTables, Name ));
tableLookup.addLookupField(fieldNum(ReferenceTables, Description ));
tableLookup.parmQuery(query);
tableLookup.performFormLookup();
Can you please help me with this?
Thanks and regards...
use sysTableLookup instead of SysReferenceTableLookup

Qt - Hash table contains incorrect values

I'm doing my controller. When I click on an item in my ListWidget, the following method is called :
void ContactBookController::setCurrentlySelectedItem(QListWidgetItem *item)
{
setCurrentItem(*item);
m_window.setEditButtonsState(true);
}
And the setCurrentItem() method is as follows : (m_current_item is a private variable):
void ContactBookController::setCurrentItem(const QListWidgetItem &current_item)
{
m_current_item = current_item;
}
Now, when I create a contact, I add an item to the QListWidget, but I also create a Contact object, but I also bind them together in a QHash so I know what QListWidgetItem corresponds to what Contact. In short, here is what I did :
void ContactBookController::createContact()
{
auto new_contact = m_contact_book.createContact();
if(new_contact != nullptr)
{
new_contact->setName(tr("New contact"));
}
auto list_item = m_window.createContact(new_contact->getName());
m_window.clearSelection();
m_contact_map.insert(list_item, new_contact);
}
Now, when clicking on a QListWidgetItem, I activate the edit button and I would like to retrieve the corresponding Contact object. However, when doing this, the Contact object doesn't seem to be correct. Indeed, if I use a method on him (like getName()), my application instantly crashes.
Here is what I did :
void ContactBookController::editContact()
{
auto list_item = m_current_item;
auto contact = m_contact_map.value(&list_item); /* doesn't work */
}
My hash table is declared as such :
QHash<QListWidgetItem*, Contact*> m_contact_map;
Any idea what I did wrong ?
Your hash has the type QHash<QListWidgetItem*, Contact>. So, mapping a item pointer to a contact value.
When you save the mapping for a specific item with m_contact_map.insert(list_item, new_contact), you add a mapping from the item pointer to the contact. But when you try to retrieve the contact with m_contact_map.value(&list_item), you look up the value for the pointer to the local list_item variable, which points to somewhere on the stack, and has nothing to do with the pointer to the item that is shown in the view.
Either you need to save to pointer to the selected value, i.e. make m_current_item a QListWidgetItem *m_current_item, or you simply use QListWidget::currentItem() to retrieve the current item without the need for an additional member variable.
(Side note: You should check for currentItem() != nullptr, since a list widget does not necessarily has an item selected.)

How to select all member which has a given attribute name with UDA?

Considering an attribute which take a delegate ( predicate function as std.algorithm.filter )
struct Section( alias pred ){}
This is used to annotate a field like this:
struct A {
#Section!( ( words ) => words[0] == '#' )
string b;
int c;
}
Field b is annotate by a delegate which return true if a string start by # when called
So how to retrieve all field which are annotated by #Section ?
Is it possible to called at runtime his delegate with a string as parameter and know if is true or not ?
thanks
So how to retrieve all field which are annotated by #Section ?
First, use allMembers or .tupleof to enumerate over all the fields of the struct.
Then, enumerate over all attributes attached to each field using getAttributes. Check if #Section is present in the field.
Is it possible to called at runtime his delegate with a string as parameter and know if is true or not ?
You should save an alias within the Section structure. For example:
struct Section(alias pred)
{
alias fun = pred;
}
Then, just reference the getAttributes result tuple member.

Sort a list based on URL parameter (or sort nested domain model in query)

I'm sure there is a way to do this, but I'm really stuck on this one.
I have a domain model that connects to entities Foo and Bar in a many-to-many-relationship. Now when I want to list all Foos to a certain Bar, I do the query and get a lot of FooBar objects. I iterate through these objects and add all Foos to a list.
Like so:
def fooBarRelations = FooBar.findAllByBar bar
def fooList = []
fooBarRelations.each { fooList.add it.foo }
How can I sort the fooList based upon the parameters a g:sortableColumn adds to the url namely sort (the field to sort) and order.
I know you can pass the parameters to the query directly but I think this is not possible in my case?
So how can I either
Make one query without list iterating so I can pass in the sorting parameters OR
Sort my custom list based upon the sorting parameters?
Addition 1 (03/25/2012)
If I could to this ...
def fooBarRelations = FooBar.findAllByBar bar, [sort: 'foo.' + params.sort, order: params.order]
... the problem would be solved. But passing this to the query does not have any effect on the output. Is there any way I can sort a query by a sub-property?
If you really can't sort within the query itself. Then you need a list of lists.
List<List<Fields>> mylist;// where List<Fields> is a lists of the fields.
Then use a Comparator to sort your List> by the desired filed. Say your desired field is at index 3:
new Compare(List<Fields> L1, List<Fields> L2){
if(L1.get(3)>L2.get(3))
return -1;//etc.
UPATE BASED ON COMMENT:
say your entity is as follows
public class Entity{
String name, address, school;
Integer bankaccount;
//etc...
}
Then
public class WhereISort{
List<Entity> myList;
String mysorter;//mysorter can be declared here as static final
public WhereISort(){//maybe pass list in here or whatever
}
public Response myWebService(params..., String sorter){
mysorter=sorter;//mysorter can be declared here as static final
Collections.sort(myList, new Comparator() {
public int compare(Entity e1, Entity e2) {
if(mysorter.equalsIgnoreCase("name")){
return e1.getName().compareToIgnoreCase(e1.getName());
}else if(mysorter.equalsIgnoreCase("bankaccount")){
//your code here, etc.
}
}
});
}
}
Of course, the main point is using "mysorter" and the inner class "Comparator" to sort

C++/Qt Multiline strings; also, multiple queries

Two [hopefully] quick questions regarding C++/Qt. Is the following proper for writing a string on multiple lines?
QString strQuery;
strQuery="\
CREATE TABLE foo\
(bar integer primary key,\
baz varchar(20))";
I believe this is right, but in Qt Creator it doesn't highlight as though it is one big string.
Secondly, will QSqlQuery.exec() run multiple queries in a single execution or does each query need to be run through exec()? For example, I'm trying something like:
QSqlQuery query;
QString strQuery;
strQuery="\
CREATE TABLE foo \
(bar integer primary key,\
baz varchar(10));\
CREATE TABLE herp\
(de integer primary key, \
derp varchar(10))";
query.exec(strQuery);
From what I can see, only that first table is being created. I don't know if this is related to my multiline string, to my database type (SQLite), or just QSqlQuery in general.
Thanks for the help!
I think that will be the right way:
QString strQuery;
strQuery="CREATE TABLE foo " \
"(bar integer primary key, " \
"baz varchar(20));";
// with this style `strQuery` will be single line, like "CREATE TABLE foo (bar integer primary key, baz varchar(20));"
QSqlQuery query;
QString strQuery;
strQuery="CREATE TABLE foo " \
"(bar integer primary key, " \
"baz varchar(10));"
query.exec(strQuery);
strQuery="CREATE TABLE herp " \
"(de integer primary key, " \
"derp varchar(10))";
query.exec(strQuery);