Skip to content

Commit 33f81ef

Browse files
committed
Added independant opaque return types for all calls.
1 parent 6f65250 commit 33f81ef

File tree

4 files changed

+189
-40
lines changed

4 files changed

+189
-40
lines changed

Firebase.cpp

+105-7
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,40 @@ String makeUrl(const String& path, const String& auth) {
3131
return url;
3232
}
3333

34+
class FirebaseCall {
35+
public:
36+
FirebaseCall(const String& host, const String& auth,
37+
const char* method, const String& path, const String& value,
38+
HTTPClient* http);
39+
FirebaseCall(const String& host, const String& auth,
40+
const char* method, const String& path,
41+
HTTPClient* http);
42+
43+
44+
// True if there was an error completing call.
45+
bool isError() const;
46+
String errorMessage() const;
47+
48+
// True if http status code is 200(OK).
49+
bool isOk() const;
50+
51+
// Message sent back from Firebase backend. This pulls value to local memory,
52+
// be careful if value can be large.
53+
String rawResponse();
54+
55+
int httpStatus() const {
56+
return status_;
57+
}
58+
59+
private:
60+
FirebaseCall(HTTPClient* http);
61+
62+
HTTPClient* http_;
63+
64+
int status_;
65+
String error_message_;
66+
};
67+
3468
} // namespace
3569

3670
Firebase::Firebase(const String& host) : host_(host) {
@@ -42,24 +76,36 @@ Firebase& Firebase::auth(const String& auth) {
4276
return *this;
4377
}
4478

45-
FirebaseCall Firebase::get(const String& path) {
46-
return FirebaseCall(host_, auth_, "GET", path, &http_);
79+
FirebaseGetResult Firebase::get(const String& path) {
80+
FirebaseCall call(host_, auth_, "GET", path, &http_);
81+
return call.isError() ? FirebaseGetResult::FromError(call.errorMessage())
82+
: FirebaseGetResult::FromResponse(call.rawResponse());
4783
}
4884

49-
FirebaseCall Firebase::push(const String& path, const String& value) {
50-
return FirebaseCall(host_, auth_, "POST", path, value, &http_);
85+
FirebasePushResult Firebase::push(const String& path, const String& value) {
86+
FirebaseCall call(host_, auth_, "POST", path, value, &http_);
87+
return call.isError() ? FirebasePushResult::FromError(call.errorMessage())
88+
: FirebasePushResult::FromResponse(call.rawResponse());
5189
}
5290

53-
FirebaseCall Firebase::remove(const String& path) {
54-
return FirebaseCall(host_, auth_, "DELETE", path, &http_);
91+
FirebaseRemoveResult Firebase::remove(const String& path) {
92+
FirebaseCall call(host_, auth_, "DELETE", path, &http_);
93+
if (call.isError()) {
94+
return FirebaseRemoveResult::FromError(call.errorMessage());
95+
}
96+
// Remove is only complete if returned status is OK(200).
97+
if (!call.isOk()) {
98+
return FirebaseRemoveResult::FromError(
99+
"Remove " + path + " returned with status " + call.httpStatus());
100+
}
101+
return FirebaseRemoveResult::Ok();
55102
}
56103

57104
FirebaseEventStream Firebase::stream(const String& path) {
58105
return FirebaseEventStream(host_, auth_, path);
59106
}
60107

61108
/* FirebaseCall */
62-
63109
FirebaseCall::FirebaseCall(const String& host, const String& auth,
64110
const char* method, const String& path, const String& value,
65111
HTTPClient* http) : http_(http) {
@@ -154,4 +200,56 @@ String FirebaseEventStream::errorMessage() const {
154200
return error_message_;
155201
}
156202

203+
FirebaseEventStream::operator bool() {
204+
return !isError() && connected();
205+
}
206+
207+
/* FirebaseResult */
208+
209+
FirebaseResult::FirebaseResult(const String& error_message)
210+
: is_error_(true), error_message_(error_message) {}
211+
212+
FirebaseResult::FirebaseResult() {}
213+
214+
FirebaseResult::operator bool() const {
215+
return !isError();
216+
}
217+
218+
bool FirebaseResult::isError() const {
219+
return is_error_;
220+
}
221+
222+
const String& FirebaseResult::errorMessage() const {
223+
return error_message_;
224+
}
225+
226+
/* FirebaseRemoveResult */
227+
228+
FirebaseRemoveResult::FirebaseRemoveResult(const String& error_message)
229+
: FirebaseResult(error_message) {}
230+
231+
FirebaseRemoveResult::FirebaseRemoveResult() {}
232+
233+
234+
/* FirebasePushResult */
235+
236+
FirebasePushResult::FirebasePushResult(const String& error_message)
237+
: FirebaseResult(error_message) {}
238+
239+
FirebasePushResult::FirebasePushResult() {}
240+
241+
const String& FirebasePushResult::name() const {
242+
return name_;
243+
}
244+
245+
/* FirebaseGetResult */
246+
247+
FirebaseGetResult::FirebaseGetResult(const String& error_message)
248+
: FirebaseResult(error_message) {}
249+
250+
FirebaseGetResult::FirebaseGetResult() {}
251+
252+
const String& FirebaseGetResult::rawResponse() {
253+
return response_;
254+
}
157255

Firebase.h

+77-26
Original file line numberDiff line numberDiff line change
@@ -25,9 +25,9 @@
2525
#include <WiFiClientSecure.h>
2626
#include <ESP8266HTTPClient.h>
2727

28-
//TODO(edcoyne) split these into multiple files.
29-
30-
class FirebaseCall;
28+
class FirebaseGetResult;
29+
class FirebasePushResult;
30+
class FirebaseRemoveResult;
3131
class FirebaseEventStream;
3232

3333
// Primary client to the Firebase backend.
@@ -38,55 +38,103 @@ class Firebase {
3838

3939
// Fetch result at "path" to a local variable. If the value is too large you will exceed
4040
// local memory.
41-
FirebaseCall get(const String& path);
41+
FirebaseGetResult get(const String& path);
4242

4343
// Add new value to list at "path", will return child name of new item.
44-
FirebaseCall push(const String& path, const String& value);
44+
FirebasePushResult push(const String& path, const String& value);
4545

4646
// Deletes value at "path" from server.
47-
FirebaseCall remove(const String& path);
47+
FirebaseRemoveResult remove(const String& path);
4848

4949
// Starts a stream of events that effect object at "path".
5050
FirebaseEventStream stream(const String& path);
5151

5252
private:
53+
54+
int sendRequest(const char* method, const String& path, const String& value);
55+
5356
HTTPClient http_;
5457
String host_;
5558
String auth_;
5659
};
5760

58-
class FirebaseCall {
61+
62+
// Result from a Firebase call.
63+
class FirebaseResult {
5964
public:
60-
FirebaseCall(const String& host, const String& auth,
61-
const char* method, const String& path, const String& value,
62-
HTTPClient* http);
63-
FirebaseCall(const String& host, const String& auth,
64-
const char* method, const String& path,
65-
HTTPClient* http);
65+
// Constructor for error result.
66+
FirebaseResult(const String& error_message);
67+
// Constructor if no error.
68+
FirebaseResult();
6669

70+
// True if no error.
71+
operator bool() const;
6772

68-
// True if there was an error completing call.
6973
bool isError() const;
70-
String errorMessage() const;
7174

72-
// True if http status code is 200(OK).
73-
bool isOk() const;
75+
const String& errorMessage() const;
76+
77+
private:
78+
bool is_error_ = false;
79+
String error_message_;
80+
};
7481

75-
// Message sent back from Firebase backend. This pulls value to local memory,
76-
// be careful if value can be large.
77-
String rawResponse();
82+
class FirebaseRemoveResult : public FirebaseResult {
83+
public:
84+
static FirebaseRemoveResult FromError(const String& error_message) {
85+
return FirebaseRemoveResult(error_message);
86+
}
7887

79-
int httpStatus() const {
80-
return status_;
88+
static FirebaseRemoveResult Ok() {
89+
return FirebaseRemoveResult();
8190
}
8291

8392
private:
84-
FirebaseCall(HTTPClient* http);
93+
FirebaseRemoveResult(const String& error_message);
94+
FirebaseRemoveResult();
95+
};
8596

86-
HTTPClient* http_;
97+
class FirebasePushResult : public FirebaseResult {
98+
public:
99+
static FirebasePushResult FromError(const String& error_message) {
100+
return FirebasePushResult(error_message);
101+
}
87102

88-
int status_;
89-
String error_message_;
103+
static FirebasePushResult FromResponse(const String& response) {
104+
FirebasePushResult result;
105+
// TODO(edcoyne): add json parsing to get name object.
106+
result.name_ = response;
107+
return result;
108+
}
109+
110+
const String& name() const;
111+
112+
private:
113+
FirebasePushResult(const String& error_message);
114+
FirebasePushResult();
115+
116+
String name_;
117+
};
118+
119+
class FirebaseGetResult : public FirebaseResult {
120+
public:
121+
static FirebaseGetResult FromError(const String& error_message) {
122+
return FirebaseGetResult(error_message);
123+
}
124+
125+
static FirebaseGetResult FromResponse(const String& response) {
126+
FirebaseGetResult result;
127+
result.response_ = response;
128+
return result;
129+
}
130+
131+
const String& rawResponse();
132+
133+
private:
134+
FirebaseGetResult(const String& error_message);
135+
FirebaseGetResult();
136+
137+
String response_;
90138
};
91139

92140
class FirebaseEventStream {
@@ -108,6 +156,9 @@ class FirebaseEventStream {
108156
// True if there is an event available.
109157
bool available();
110158

159+
// True if no error and stream is connected.
160+
operator bool();
161+
111162
// True if there was an error.
112163
bool isError() const;
113164
String errorMessage() const;

examples/FirebasePush_ESP8266/FirebasePush_ESP8266.ino

+6-6
Original file line numberDiff line numberDiff line change
@@ -38,20 +38,20 @@ void setup() {
3838
Serial.println(WiFi.localIP());
3939

4040
// add a new entry.
41-
FirebaseCall push = fbase.push("/logs", "{\".sv\": \"timestamp\"}");
42-
if (push.isError()) {
41+
FirebasePushResult push = fbase.push("/logs", "{\".sv\": \"timestamp\"}");
42+
if (!push) {
4343
Serial.println("Firebase request failed");
4444
Serial.println(push.errorMessage());
4545
return;
4646
}
4747

4848
// print response.
49-
Serial.println(push.rawResponse());
49+
Serial.println(push.name());
5050

5151
// print all entries.
52-
FirebaseCall fetch = fbase.get("/logs");
53-
if (!fetch.isError()) {
54-
Serial.println(fetch.rawResponse());
52+
FirebaseGetResult get = fbase.get("/logs");
53+
if (get) {
54+
Serial.println(get.rawResponse());
5555
}
5656
}
5757

examples/FirebaseStream_ESP8266/FirebaseStream_ESP8266.ino

+1-1
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ void setup() {
4747

4848
void loop() {
4949
static FirebaseEventStream stream = fbase.stream("/bitcoin");
50-
if (stream.isError()) {
50+
if (!stream) {
5151
Serial.println("streaming error");
5252
Serial.println(stream.errorMessage());
5353
}

0 commit comments

Comments
 (0)