0

I am just learning an Arduino so this is totally educational purpose call.

I want to instantiate PubSubClient client with WiFiClient parameter.


#include <WiFiClient.h>
#include <PubSubClient.h>

WiFiClient *wifi = NULL;
PubSubClient client(wifi);

void setup() {
  // put your setup code here, to run once:
}

void loop() {
  // put your main code here, to run repeatedly:
}

compilation gives me back:

Compilation error: no matching function for call to /home/tepo/Arduino/libraries/PubSubClient/src/PubSubClient.h:116:4: note:   candidate expects 0 arguments, 1 provided
/home/tepo/Arduino/libraries/PubSubClient/src/PubSubClient.h:88:7: note: candidate: 'PubSubClient::PubSubClient(const PubSubClient&)'
 class PubSubClient : public Print {
       ^~~~~~~~~~~~
/home/tepo/Arduino/libraries/PubSubClient/src/PubSubClient.h:88:7: note:   no known conversion for argument 1 from 'WiFiClient*' to 'const PubSubClient&'

exit status 1

Compilation error: no matching function for call to 'PubSubClient::PubSubClient(WiFiClient*&)'

and listing all the other constructors.

type chain seems to hold: class WiFiClient : public ESPLwIPClient -> class ESPLwIPClient : public Client -> class Client: public Stream

PubSubClient ctor:

 PubSubClient(Client& client);

so why is it not accepting a WifiClient as a parameter?

2
  • PubSubClient client(*wifi);. it will compile, but it will just crash in runtime since there will be no WiFiClient object at address 0
    – Juraj
    Nov 17, 2023 at 15:37
  • look at the example code in the library
    – jsotola
    Nov 17, 2023 at 15:43

1 Answer 1

1

The issue you're encountering with the PubSubClient constructor in Arduino is related to how you're passing the WiFiClient object. You're currently using a pointer (WiFiClient *wifi), but the PubSubClient constructor expects a reference to a Client object, not a pointer.

The WiFiClient class inherits from the Client, so it can be used with PubSubClient. However, you need to pass an instance of WiFiClient, not a pointer to an instance.

Here's how you can correct your code:

#include <WiFiClient.h>
#include <PubSubClient.h>

WiFiClient wifi;
PubSubClient client(wifi);

void setup() {
  // put your setup code here, to run once:
}

void loop() {
  // put your main code here, to run repeatedly:
}

In this corrected version, wifi is an instance of WiFiClient, not a pointer. When you pass wifi to the PubSubClient constructor, it correctly matches the expected Client& client parameter type.

In C++ a pointer (WiFiClient *) is a variable that holds the memory address of an object. A reference (WiFiClient &) is an alias for an object. The PubSubClient constructor expects a reference because it needs to interact with the Client object throughout its lifecycle, and references are generally safer and more straightforward to use in this context than pointers.

2
  • yeah, that got it working; however I'm failing to understand where the actual instance of 'wifi' is comming from as I'm not constructing int, rather in the sketch I am using WifiManager that seems 'injecting' it to the declared variable. (I come from java-spring world) That's why I thought pointer will do in this case; it seems a bit weird to me it just "gets supplied" somehow..
    – greengold
    Nov 18, 2023 at 21:48
  • What do you mean you're not constructing it? WiFiClient wifi; constructs it. Unlike Java you don't need to do a new procedurally to instantiate a class variable.
    – Nick Gammon
    Nov 19, 2023 at 7:37

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.