finder
finder

Reputation: 145

Sqlite database file managing in Swift 3 and iOS (copy from local and/or bundle to app)

I'm trying to upload my sqlite database file into an application. I've been learning about the iOS file system, and I'm not completely sure how it works and got lost. This is what I would like to achieve, but not sure how:

  1. I would like to have database on this location my-xcode-project-path/data/foo.sqlite. Now I'm running simulator for first time, and I would like to copy this database into simulator's Document directory.
  2. In case if I had the application already installed, I would skip step 1. and copy database from bundle.
  3. If I tried to run simulator, but don't have file available in bundle, I would like to keep that database.

Thank you in advance!!!

My code is looking like this:

func prepareDatabaseFile() -> String {
    let fileName: String = "foo.sqlite"

    let filemanager:FileManager = FileManager.default
    let directory = filemanager.urls(for: .documentDirectory, in: .userDomainMask).first!

    let newUrl = directory.appendingPathComponent(fileName)
    let bundleUrl = Bundle.main.resourceURL?.appendingPathComponent(fileName)

    // check bundle
    if filemanager.fileExists(atPath: (bundleUrl?.path)!) {
        print("bundle file exists!")
        return (bundleUrl?.path)! //probably I need to copy from bundle to new app and return new url
    // here check if file already exists on simulator, but not in bundle
    } else if filemanager.fileExists(atPath: (newUrl.path)) {
        print("prebuild file exists!")
        return newUrl.path //no copy is needed
    // finally, if nothing I need to copy local file
    } else {
        //todo copy local file from the path my-xcode-project-path/data/foo.sqlite
        print("todo")
    }

    return fileName
}

Upvotes: 4

Views: 3620

Answers (2)

Hiren
Hiren

Reputation: 270

  self.copyfile(filename: "mydata.sqlite" )

        return true
    }

    func copyfile(filename : String)
    {
        let dbpath : String = getpath(filename: filename as String)

        let filemanager = FileManager.default

        if filemanager.fileExists(atPath: dbpath)
        {
            let documentsURl = Bundle.main.resourceURL

            let frompath = documentsURl?.appendingPathComponent(filename)

            print(frompath)

        }



    }

    func getpath(filename: String) -> String
    {

        let documentsURL = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask)[0]

        print(documentsURL)

        let fileURL = documentsURL.appendingPathComponent(filename as String)

        print(fileURL.path)
        return fileURL.path




    }

Upvotes: 0

finder
finder

Reputation: 145

With @Rob's help, I came to following solution which satisfied my requirement. Previously it was necessary to add sqlite file into xcode project, with proper target.

func prepareDatabaseFile() -> String {
    let fileName: String = "foo.sqlite"

    let fileManager:FileManager = FileManager.default
    let directory = fileManager.urls(for: .documentDirectory, in: .userDomainMask).first!

    let documentUrl= directory.appendingPathComponent(fileName)
    let bundleUrl = Bundle.main.resourceURL?.appendingPathComponent(fileName)

    // here check if file already exists on simulator
    if fileManager.fileExists(atPath: (documentUrl.path)) {
        print("document file exists!")
        return documentUrl.path
    else if fileManager.fileExists(atPath: (bundleUrl?.path)!) {
        print("document file does not exist, copy from bundle!")
        fileManager.copyItem(at:bundleUrl, to:documentUrl)
    }

    return documentUrl.path
}

Upvotes: 5

Related Questions