I record and save an audio file, this works and plays in the app as expected.
After the recording, however, I try to load it so I can pass the audio into a JSON object, but can't open it.
I get the following error:
The file “audio.m4a” couldn’t be opened because the text encoding of its contents can’t be determined.
This is call I'm making:
do {
let audioData = try NSData(contentsOfFile: String(contentsOf: audioURL!))
} catch {
print error
}
Any ideas how I can load the audio data as from the file in base64 encoding?
Thanks
You didn't explain how do you save your file, so i can only assume (according to file extension), that you are not saving it as base64 string.
Please refer to first answer of this question. To check if you save audio file as base64 string correctly.
But still you can use other way. At first load data:
let audioData = try Data(contentsOf: audioURL!)
Then convert it to base64 string:
let encodedString = audioData.base64EncodedString()
The problem is that you are using the wrong method. The audio data it is not a string it is a collection of bytes (an array of UInt8). To read your audio data you need to use the Data initializer Data(contentsOf: audioURL) and convert this data to base64 string using Data instance method base64EncodedString.
if let base64String = try? Data(contentsOf: audioURL).base64EncodedString() {
print(base64String)
}
Related
I have json in below format which I am fetching from server and parsing using SwiftyJSON.
{
name: "Ganesh"
imageURL:"www.abc.com/image.png"
}
I am downloading image using below code :
do{
let myData = try Data(contentsOf: url)
}catch{
Print("error")
}
Note: "url" contains url from json which is converted from string to URL
I want to save this "myData" in same json above with different key and access the same in future.
I am trying to save myData in json using SwiftyJSON method :
responseJSON["image"] = try JSON(data: myData)
Error which I am receiving :
"if Error while converting data into json The data couldn’t be read because it isn’t in the correct format."
I am not getting what is the problem?
Image is present at that url. if I convert myData into UIImage and If I assign it on UIImageView I can see it.
If you want to save an image in JSON, the best way would be to convert Data to Base64 string
if let base64encodedString = myData.base64EncodedString(){
responseJSON["image"] = base64encodedString
}
To restore image, try this
guard let base64encodedString = responseJSON["image"] as? String else { return }
guard let imageData = Data(base64Encoded: base64encodedString) else { return }
let image = UIImage(data: imageData)
Although Base64 - encoded images take approximately 33% more space than raw data, they are web and database safe - base64 strings contain neither control characters, nor quotes, and can be transferred as parameter in URL query strings.
Can I get storyboard XML source code programmatically somehow and send it to server?
For example:
let sourceCode = storyboard.getCode()
Or maybe can I send the whole file to server and have the server parse it by itself?
Well you can read the content of the storyboard-file if you know its name.
let filePath = NSBundle.mainBundle().URLForResource("MyStoryboard", withExtension: "storyboard")
let fileURL = NSURL(string: filePath)
do {
let filecontent = try String(contentsOf: fileURL, encoding: .utf8)
//submit filecontent to your server
}
catch {/* error handling here */}
This will give you the filecontent as a string. If you need to parse it as XML you will need to use some kind of XML-parser like e.g. NSXMLParser.
I'm struggling to get an image file loaded in Swift 3.
Here is the code:
do {
let imageData = try Data(contentsOf: imageUrl2.asURL())
} catch {
print ("loading image file error")
}
And the current Url String is:
file:///Users/veikoherne/Library/Developer/CoreSimulator/Devices/889A08D5-B8CC-458C-99FF-643A4BA1A806/data/Containers/Data/Application/F64ED326-7894-4EE7-AA3B-B1BB10DF8259/Documents/img2017-03-23 17:39:24.jpg
and obviously I have checked that this file exists and is valid image. It always ends up telling me "loading image file error". Anyone have experiences loading local data in Swift 3?
The answer mentioned was using NSData object and probably Swift 2. Current Swift 3 refuses to bridge NSData to Data, that's why I have to use Data.
Loading data from local file you should use "contentsOfFile:" method.
Reference link: https://www.hackingwithswift.com/example-code/strings/how-to-load-a-string-from-a-file-in-your-bundle
So in case of reading data you can use:
Data(contentsOf: <URL>, options: <Data.ReadingOptions>)
Reading a plain text as a String, use:
String(contentsOfFile: <LocalFileDirPath>)
Reading an image from document directory, use:
UIImage(contentsOfFile: <LocalFileDirPath>)
Hope this would be helpful!
I experienced the same issue when trying to retrieve a file that I just downloaded. If you have saved a file from some url like I did, this should work:
let documentDirectory = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first
let localUrl = documentDirectory.appendingPathComponent("somefile.txt")
if FileManager.default.fileExists(atPath: localUrl.path){
if let cert = NSData(contentsOfFile: localUrl.path) {
return cert as Data
}
}
Swift 5 version.
func loadFileFromLocalPath(_ localFilePath: String) ->Data? {
return try? Data(contentsOf: URL(fileURLWithPath: localFilePath))
}
I am using NSUserDefaults.standardUserDefaults() to save my JSON String got from WebService to iPhone memory. When I load it to use with my parser function, the processing speed is so slow. I don't want to use RealmIO or any database because that thing doesn't necessary. I would like to ask is there any way faster than NSUserDefaults? Please check my JSON file (I need store more than 20 files like that)
Instead of saving your data to NSUserDefaults, you should save it to a different file, this will be much more efficient.
Here is how you can do it :
// Build file url
let documentsURL = NSFileManager.defaultManager().URLsForDirectory(.DocumentDirectory, inDomains: .UserDomainMask).last!
let fileURL = documentsURL.URLByAppendingPathComponent("file_1.json", isDirectory: false)
// Write
let jsonString = "..."
let jsonData = jsonString.dataUsingEncoding(NSUTF8StringEncoding)
do {
try jsonData?.writeToURL(fileURL, options: NSDataWritingOptions())
} catch {
NSLog("Writing file to `\(fileURL)` failed with error : \(error)")
}
// Read
do {
let jsonData = try NSData(contentsOfURL: fileURL, options: NSDataReadingOptions())
let jsonString = String(data: jsonData, encoding: NSUTF8StringEncoding)
} catch {
NSLog("Reading file at url `\(fileURL)` failed with error : \(error)")
}
NSUserDefaults is not a database. If your JSON documents are more than 100 KB altogether store them into separate documents. Note that every time you change any user default, all the user defaults have to be written to a file. If you have 20 JSON documents of 1MB each, that's writing 20MB or more for every user default the you change.
So my app is using a JSON API response to read some data from server. Since the API is not yet ready i want to use a sample JSON file which is stored in my app itself. Since all my code uses SwiftyJSON i want to stick to it for the local file.
I am doing the following in my ViewDidLoad method and somehow this end result is a blank array. Do you know what should i change in this code to make it work?
//Direct JSON
if let path = NSBundle.mainBundle().pathForResource("XXYYXZZfile", ofType: "json")
{
do{
let pathAsData = try NSData(contentsOfFile: path, options: NSDataReadingOptions.DataReadingMappedIfSafe)
let json = JSON(pathAsData)
print(json)
} catch{
print("Some error")
}
}
When using SwiftyJSON with NSData you have to specify the "data:" parameter for the JSON initializer:
let json = JSON(data: pathAsData)
otherwise it tries to use other available initializers and will fail with an error or even, like in your case, will fail silently with a misinterpreted input and wrong output.