[SOLVED] how to disconnect a certain client user from server



  • I have a client / server app. in the server, i want to disconnect a certain user. with this user, the username is known and the ip address. how to disconnect this user only, while everyone else in the client is still online. i have tried the following with out any luck.

    @clients.remove(client) //error: no matching function for call to 'QSet<QTcpSocket*>::remove(QString&)'
    clients.contains("test"); error: no matching function for call to 'QSet<QTcpSocket*>::contains(const char [4])'
    @

    i am trying to remove the user test from the client from server. since only the name and ip address is known, this variables is stored as a variable or string. your help is much appreciated.



  • This isn't true, is it?
    How come that you "again":/forums/viewthread/13197/ are not able to read the documentation and doing the very same error within three days? How come that you think that a QSet<QTcpSocket *> takes a QString as argument for remove if you do not put a QString into the add() method?

    Feel free to lookup QHash and/or QMap and good look on your attempt to destroy the world ... you're on a good way, I'm sure.



  • have a nice day too :)



  • Volkers wording may have been a bit harsh, but the point he tries to bring across is valid IMO. I have told him so, and I think he agrees.

    You had a very similar issue just the other day where you tried to use a method with an argument that it didn't take (I think it was a QModelIndex instead of an int, from the top of my head), and then you posted a message with basically just that error asking what's wrong. Now, you do the exact same thing, getting the same error. People don't mind helping you, but it would be good if you showed that you are learning from that. Posting basically the same issue multiple times is very frustrating for everyone involved.

    So please, do take the time to learn what your error messages mean. They are really quite informative, most of the time (errors related to template meta programming may become very cryptic indeed, but that's not what is going on here). Then, if you run into an issue like this, have another good, long, hard look at the documentation of the relevant classes. Does the class actually have the method you want, with the right types of arguments?

    Then, last but not least, please don't fight out your grievances in public. There is a "report" link next to every posting. Using it for posts you feel are offending is a perfectly legit use for that feature. I can assure you that moderators are also just humans, and they are also told off if they step over the line by our "Forum Queen" Alexandra. If you want to address Volker, then use the email feature of the forums.



  • ok Andre, i will report next time. it is just that i am a bit frustrated with the reading of my books and the study online

    what i need is an explanation as to why i am not able to do something. i really need to get this to work.

    i have tried my best in c++ and i am still stuck with this problem. would someone kind care to help me here please. the code below is my attempt in solving this issue.

    @ QMapIterator <QTcpSocket, int> test;

    QString nick = str;
    test.insert(nick, 1);
    //test = QAbstractSocket::peerName();

    str.remove(nick.toLower());@

    all i want to do is delete a user from client. i really need a step by step example here. can someone take the time to help me. all i have is a user name and an ip address and i need to boot that person from the client. volker said that i need a qmap but that is not enough information for me to solve this. thank you

    sorry volker if i offender you.



  • You are not being "run down" because you "don't know enough", pholcer just vented his frustration on you not showing that you learned something of your last post. Learning how to program, and especially to program well, is a long an sometimes frustrating road. It does not help to learn multiple languages at the same time, though it does help to learn more than one in the long run.

    On what you need: opinions on that may differ between you and the people answering. You may be of the opinion that you just need a bite-sized bit of information, while the people who have that knowedge may think that you need to learn how to find that information yourself the next time. Otherwise, they are afraid that the next time you need another bite-sized bit of information, you will come back and ask for that one, instead of having learned how to find it yourself. It's like with the hungry: the hungry man might just want food, but it pays off to spend the time to teach him how to fish instead if he shows the aptitude to learn.

    I considder this meta-discussion now closed. Please don't continue it here. If you really feel a need, open a topic in the DevNet meta forum. I will close this topic if you, or somebody else, continues this issue here.

    Anyway, back on topic:
    In your code section above, it is very unclear what you are trying to do, as we cannot see the types of the variables you use. It looks as if you are trying to remove something from a QString though? And what is that QMapIterator doing there? What map is it related to? Note that using a QTcpSocket as a key can't work. QTcpSockets are QObjects, and these can not be copied, so they are useless as keys.



  • [quote author="kalster" date="1326183713"]all i want to do is delete a user from client. i really need a step by step example here. can someone take the time to help me. all i have is a user name and an ip address and i need to boot that person from the client. volker said that i need a qmap but that is not enough information for me to solve this.[/quote]

    Honestly, there is no way one can provide you a step by step example here. There are so many questions left unanswered: what is a user, what is a client in your case, what does boot mean, how are all those things are actually tied together in your application and how do they map to application objects.

    There are specific answers to specific questions and there are general answers to general questions - you cannot have both. So if you need specific assistance you will have to provide (a whole lot) more information - otherwise all you'll get is a general solution - which might map to your problem, or not - like this:

    If you want to store some value accessible by a key you will have to select an associative container - which is basically QMap or QHash. As both are template classes they allow you to freely select the types for the key (Key) and the value (T), as long as they provide a default constructor, a copy constructor and an assignment operator. This means you can use QHostAddress as Key, but you will have to use QObject* or QTcpSocket* in your case instead of QObject as T (QObject and QObject* are different types).
    @
    QHash<QHostAddress, QTcpSocket*> clients;

    QTcpSocket* client = new QTcpSocket;
    ...

    // client connected, add to list
    clients.insert(client->peerAddress(), client);
    ...

    // disconnect and remove client with QHostAddress address
    QTcpSocket* client = clients.value(address);
    client->close();
    client->deleteLater();
    clients.remove(address);
    ...
    @
    Brain to terminal. Not tested. Exemplary.



  • i guess i never made my point clear. lets say the user is joe. i want to boot (ban) only joe from the client. everyone else in the client is still able to post a message.

    at the server side. i know that joe is online. i need to boot him from the server.

    i cant use clients.remove(client) because client could be anyone. clients.remove("joe") give a tcpserver error.

    the server is online and the only needed information is what i gave in my above post.

    @ QMapIterator <QTcpSocket, int> test;
    QString nick = str;
    test.insert(nick, 1);
    str.remove(nick.toLower());
    @

    in the last line of code, i am trying to remove joe from the client from server.. but it is not working. i get an error that a string cannot be used, which is why i used the maplterator in the first place.

    from the server i need to only close the client joe. everyone else is still able to post. i would like to create a banning option for the server.



  • Please re-read Lukas' message. You are not giving enough information. I already pointed out the many issues and missing context of the small snippet you are posting, but yet you simply re-post it. You are telling us nothing about how users map to sockets, or where you keep that information your application. Yet you expect us to somehow know all that.



  • header
    private:
    @QSet<QTcpSocket*> clients;
    QMap<QTcpSocket*,QString> users;@

    main.cpp
    my users are connected by...
    QTcpSocket client = (QTcpSocket)sender();
    clients.insert(client);
    clients is the current client connected.

    i remove the current user by...
    clients.remove(client);

    but i am not able to remove a username from the client.

    hope this helps.



  • As I'm still not quite sure about your problem I just assume that you want to get a specific QTcpSocket* stored in <code>users</code>, identified by the QString it associates with - which means you want to access a specific value, not key.

    This can be done by manually iterating over the values using QMapIterator, but to me the most painless way in your case will be using "qFind":http://www.youtube.com/watch?v=-xGGPfdQ-n4.
    @
    QMap<QTcpSocket*, QString>::iterator user = qFind(users.begin(), users.end(), "joe");
    if(user != users.end())
    {
    QTcpSocket* socket = user.key();
    QString name = user.value();
    }
    @
    Brain to terminal. Not tested. Exemplary.

    This thread is a prime example of the endless importance to obey the "smart questioning rules":http://www.catb.org/~esr/faqs/smart-questions.html. If the question would have been "How to find a value stored in a container" it has been answered in the first reply.



  • Lukas Geyer with your code, i tried to remove your code with my code at the end of it. the user does not get disconnected.

    what more information do you need so that i can get this issue closed?

    @clients.remove(socket);
    users.remove(socket);@



  • Of course <code>users.remove(socket)</code> doesn't close the connection to the client, it just removes the value <code>socket</code> from the collection <code>users</code>.

    If you take a look at the documentation of "QTcpSocket":http://developer.qt.nokia.com/doc/qt-4.8/qabstractsocket.html#close, which method might be suitable to close the connection?



  • ok. i will but i don't have time right now to try to close the socket or even look thoroughly into your code which looks great and should be what i am looking for. i will post my results later in the day.

    thank you for you patience



  • I thought i did not have time but i did.

    the code works great. I can now disconnect a selected user. thank you Lukas Geyer. you saved the day :)

    edit: i forgot about closing the socket.



  • ps: Andre, i fixed my few posts. they are now neater to read



  • Thanks, folks. Let's try not to yell at each other and be constructive, both on the asking and the replying end.

    All good, carry on. :)


Log in to reply
 

Looks like your connection to Qt Forum was lost, please wait while we try to reconnect.