I am exploring uploading crash log to HockeyApp but the crash log are not showing up on HockeyApp's console panel.
The format of the crash log is copied from their demo code on their website as such, with modification to Package
and CrashReporter Key
:
Package: //Bundle ID as shown on HockeyApp console
Version: 1.3
OS: Mac OS X 10.14.2 (18C54)
Manufacturer: Apple
Model: MacBookPro12,1
Date: Wed Apr 24 15:35:08 GMT+08:00 2019
CrashReporter Key: //Incident key generated in the crash log
java.lang.RuntimeException: Unable to start activity ComponentInfo\{de.codenauts.hockeyapp/de.codenauts.hockeyapp.MainActivity\}: java.lang.NullPointerException
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2787)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2803)
at android.app.ActivityThread.handleRelaunchActivity(ActivityThread.java:4066)
at android.app.ActivityThread.access$2400(ActivityThread.java:135)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2140)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:144)
...
This post suggested that the date
field may be wrong, but I have made adjustments from the demo code so I suppose it should be alright.
This post also suggested to check on the version field. The versions available on HockeyApp are as shown here, and I am targeting the version 1.3:
I have tried 1.3
, 1.3(3)
, 3
but all doesn't seem to work.
My POST request returns a statusCode
of 201 created, so I suppose the network request is successful. Am I missing something?
EDIT: POST function
This is the POST function that I use to upload the custom crash report.
func postLog(filename: String) {
let urlString = "https://rink.hockeyapp.net/api/2/apps/APP_ID/crashes/upload"
guard let url = URL(string: urlString) else {return}
guard let filepath = Bundle.main.url(forResource: filename, withExtension: nil) else {
print("Filepath nil")
return
}
let fileData = NSData(contentsOf: filepath)
var request = URLRequest(url: url)
request.httpMethod = "POST"
let boundary = "Boundary-\(UUID().uuidString)"
request.setValue("multipart/form-data; boundary=\(boundary)", forHTTPHeaderField: "Content-Type")
request.httpBody = createBody(parameters: [:], boundary: boundary, data: fileData! as Data, mimeType: "text/plain", filename: filename)
let dataTask = session.dataTask(with: request) { (data, response, error) in
if let error = error {
print(error.localizedDescription)
return
}
if let response = response {
print(response)
}
}
dataTask.resume()
}
After contacting HockeyApp Support, the problem was at the createBody
function.
The name
parameter needs to be log
instead of file
.
func createBody(parameters: [String: String],
boundary: String,
data: Data,
mimeType: String,
filename: String) -> Data {
let body = NSMutableData()
let boundaryPrefix = "--\(boundary)\r\n"
for (key, value) in parameters {
body.appendString(boundaryPrefix)
body.appendString("Content-Disposition: form-data; name=\"\(key)\"\r\n\r\n")
body.appendString("\(value)\r\n")
}
body.appendString(boundaryPrefix)
//Problem was on this line, previously it was name=\"file\". After changing to log, it worked
body.appendString("Content-Disposition: form-data; name=\"log\"; filename=\"\(filename)\"\r\n")
body.appendString("Content-Type: \(mimeType)\r\n\r\n")
body.append(data)
body.appendString("\r\n")
body.appendString("--".appending(boundary.appending("--")))
return body as Data
}