Swiftpack.co - Package - mongodb/mongo-swift-driver

Build Status Code Coverage

MongoSwift

The official MongoDB driver for Swift.

Index

Documentation

The latest documentation is available here.

Bugs / Feature Requests

Think you've found a bug? Want to see a new feature in mongo-swift-driver? Please open a case in our issue management tool, JIRA:

  1. Create an account and login: jira.mongodb.org
  2. Navigate to the SWIFT project: jira.mongodb.org/browse/SWIFT
  3. Click Create Issue - Please provide as much information as possible about the issue and how to reproduce it.

Bug reports in JIRA for all driver projects (i.e. NODE, PYTHON, CSHARP, JAVA) and the Core Server (i.e. SERVER) project are public.

Installation

MongoSwift works with Swift 5.0+ on MacOS and Linux.

Installation is supported via Swift Package Manager.

Step 1: Install the MongoDB C Driver

The driver wraps the MongoDB C driver, and using it requires having the C driver's two components, libbson and libmongoc, installed on your system. The minimum required version of the C Driver is 1.15.3.

On a Mac, you can install both components at once using Homebrew: brew install mongo-c-driver.

On Linux: please follow the instructions from libmongoc's documentation. Note that the versions provided by your package manager may be too old, in which case you can follow the instructions for building and installing from source.

See example installation from source on Ubuntu in Docker.

Step 2: Install MongoSwift

Please follow the instructions in the previous section on installing the MongoDB C Driver before proceeding.

Add MongoSwift to your dependencies in Package.swift:

// swift-tools-version:5.0
import PackageDescription

let package = Package(
    name: "MyPackage",
    dependencies: [
        .package(url: "https://github.com/mongodb/mongo-swift-driver.git", from: "VERSION.STRING.HERE"),
    ],
    targets: [
        .target(name: "MyPackage", dependencies: ["MongoSwift"])
    ]
)

Then run swift build to download, compile, and link all your dependencies.

Example Usage

Note: You should call cleanupMongoSwift() exactly once at the end of your application to release all memory and other resources allocated by libmongoc.

Connect to MongoDB and Create a Collection

import MongoSwift

let client = try MongoClient("mongodb://localhost:27017")
let db = client.db("myDB")
let collection = try db.createCollection("myCollection")

// free all resources
cleanupMongoSwift()

Note: we have included the client connectionString parameter for clarity, but if connecting to the default "mongodb://localhost:27017"it may be omitted: let client = try MongoClient().

Create and Insert a Document

let doc: Document = ["_id": 100, "a": 1, "b": 2, "c": 3]
let result = try collection.insertOne(doc)
print(result?.insertedId ?? "") // prints `.int64(100)`

Find Documents

let query: Document = ["a": 1]
let documents = try collection.find(query)
for d in documents {
    print(d)
}
// check if an error occurred while iterating the cursor
if let error = documents.error {
    throw error
}

Work With and Modify Documents

var doc: Document = ["a": 1, "b": 2, "c": 3]

print(doc) // prints `{"a" : 1, "b" : 2, "c" : 3}`
print(doc["a"] ?? "") // prints `.int64(1)`

// Set a new value
doc["d"] = 4
print(doc) // prints `{"a" : 1, "b" : 2, "c" : 3, "d" : 4}`

// Using functional methods like map, filter:
let evensDoc = doc.filter { elem in
    guard let value = elem.value.asInt() else {
        return false
    }
    return value % 2 == 0
}
print(evensDoc) // prints `{ "b" : 2, "d" : 4 }`

let doubled = doc.map { elem -> Int in
    guard case let value = .int64(value) else {
        return 0
    }

    return Int(value * 2)
}
print(doubled) // prints `[2, 4, 6, 8]`

Note that Document conforms to Collection, so useful methods from Sequence and Collection are all available. However, runtime guarantees are not yet met for many of these methods.

Usage With Kitura, Vapor, and Perfect

The Examples/ directory contains sample projects that use the driver with Kitura, Vapor, and Perfect.

Development Instructions

See our development guide for instructions for building and testing the driver.

Github

link
Stars: 144

Dependencies

Used By

Total: 0

Releases

MongoSwift 0.2.0 - 2019-12-18 20:45:28

We are pleased to announce the 0.2.0 release of the MongoDB Swift driver.

This release includes a number of major improvements, detailed in the following sections.

Please note that as of this release we now require using Swift version 5.0 or greater, and version 1.15.3 or greater of the MongoDB C driver.

Thank you to everyone who contributed to this release!

Improvements for use in multithreaded applications

MongoClients now automatically pool connections to the server. We recommend sharing clients across threads in your application when possible in order to decrease the total number of connections to the server your application has open at a time.

MongoClient, MongoDatabase, and MongoCollection are now all safe to share across threads.

Please see our new multithreading guide for more information.

New BSON API

We've significantly changed the API for the driver's BSON library to make using BSON types and constructing Documents much easier.

Please see our guide describing how to use the BSON library, including a migration guide for updating from the old API.

Other new features of note

A number of other new features have been added since our last release, including:

  • Change streams support (please see our guide on using change streams here)
  • API for specifying TLS options for use with a MongoClient

Included tickets

Bug

  • [SWIFT-395] - wtimeoutMS is truncated if set to a value > Int32.max

New Feature

  • [SWIFT-133] - Implement new count API
  • [SWIFT-173] - Implement Initial DNS Seedlist discovery spec
  • [SWIFT-174] - Implement Database Enumeration spec
  • [SWIFT-176] - Implement change streams API and basic tests
  • [SWIFT-178] - All writes retryable support
  • [SWIFT-374] - Integrate libmongoc client pool into operation execution
  • [SWIFT-471] - Allow user-specified SSL options at the client level
  • [SWIFT-489] - Errors raised by drivers should include codeName string from server response
  • [SWIFT-561] - Document connection string and URI option precedence rules
  • [SWIFT-587] - Retryable Reads
  • [SWIFT-629] - Introduce the BSON enum
  • [SWIFT-630] - Integrate BSON enum into the existing API and update tests

Task

  • [SWIFT-364] - Update minimum required version to libmongoc 1.15.3
  • [SWIFT-389] - Remove deprecated bsonEquals functions
  • [SWIFT-632] - Drop Swift 4.2 support
  • [SWIFT-645] - Remove ReadConcern(_ doc: Document) initializer
  • [SWIFT-656] - Remove embedded driver
  • [SWIFT-659] - Document should not conform to ExpressibleByArrayLiteral

Improvement

  • [SWIFT-185] - Support maxTimeMS for createIndexes and dropIndexes command
  • [SWIFT-215] - Array should conditionally conform to BSONValue
  • [SWIFT-320] - All BSONValue types should be Hashable using 4.2+ Hashable API
  • [SWIFT-375] - Ensure MongoClient, MongoCollection and MongoDatabase are thread safe
  • [SWIFT-412] - MongoDatabase.drop and MongoCollection.drop should allow specifying a WriteConcern
  • [SWIFT-501] - Rationalize how we handle client options provided in URI vs. options struct
  • [SWIFT-503] - Validate that w and wtimeoutMS are non-negative in WriteConcern initializer
  • [SWIFT-504] - ReadConcern and WriteConcern should no longer wrap mongoc types
  • [SWIFT-513] - Standardize on parameter ordering for options initializers
  • [SWIFT-514] - Make MongoDatabase and MongoCollection structs
  • [SWIFT-515] - Rationalize handling of server default vs. not-provided read concern, write concern
  • [SWIFT-517] - Return Connection to pool as soon as MongoCursor is exhausted
  • [SWIFT-522] - Move listCollections filter to top level
  • [SWIFT-526] - Standardize index command options
  • [SWIFT-600] - Decimal128.writeToCurrentPosition should pass a non-mutable pointer to bson_iter_overwrite_decimal128
  • [SWIFT-607] - Implement collection enumeration spec
  • [SWIFT-608] - Implement index enumeration spec

- 2019-06-04 23:20:56

This release includes a couple of small fixes to correct inadvertent backwards-breaking changes introduced in 0.1.1.

MongoSwift 0.1.1 - 2019-06-04 18:23:55

We are pleased to announce the 0.1.1 release of the MongoDB Swift driver.

Release Highlights

Sessions support

This release adds support for MongoDB client sessions. This allows the driver to make certain causal consistency guarantees for operations that are executed using the same session, depending on the write/read concern configuration. See the official MongoDB documentation for more information on these guarantees, and the documentation on ClientSession for example usage.

Simpler Initialization and Cleanup

Previously, we required that users call MongoSwift.initialize() before using the driver to set up some global state and resources. We've now deprecated this method, and made it so that initialization happens automatically the first time you create a MongoClient.

Additionally, note that MongoSwift.cleanup() (which should be called exactly once when your application is done using the driver) has been deprecated and renamed cleanupMongoSwift(). Please see SWIFT-402 for context on the name change.

Mutable options structs

All of the properties stored in options structs are now vars, allowing you to do things like:

var options = FindOptions()
options.batchSize =  10
options.skip = 5

Included tickets

Bug

  • [SWIFT-404] - expireAfter index option is not correctly encoded
  • [SWIFT-405] - Document.count should not be publicly settable

New Feature

Improvement

  • [SWIFT-311] - MongoClient/MongoDatabase/MongoCollection ReadPreference getters should not return Optionals
  • [SWIFT-355] - Make options properties mutable to allow changing them after creation
  • [SWIFT-402] - Handle MongoSwift name conflicts
  • [SWIFT-413] - Make properties of WriteModel implementations public

MongoSwift 0.1.0 - 2019-04-18 21:21:08

We are pleased to announce the 0.1.0 release of the MongoDB Swift driver.

Release Highlights

Swift 5 Support

This release adds support for using the driver in Swift 5.0. It also drops support for Swift versions < 4.2.

Improved Error Reporting

This release re-organizes the errors thrown by the driver to more accurately represent their sources. In particular, we now throw four classes of errors: ServerError, UserError, RuntimeError, and EncodingError/DecodingError. Each type is described in detail in the error handling guide.

BSON Improvements

This release includes a number of improvements to the BSON library. In particular:

Improved Int Handling consistency in Document

We've improved the consistency of how Ints are read from and written to Documents. Previously, Int was encoded to BSON as an int32 if it could fit, or an int64 otherwise. This could lead to situations where Ints were not round tripped properly through Documents. Now, Int behaves as the type of integer it represents on a given architecture, which means it is always round-tripped correctly. (See here for details on Swift Int's variable bitwidth.)

On 64-bit systems:

  • Int is encoded as a BSON int64
  • BSON int32s are read out of documents as Int32s
  • BSON int64s are read out of documents as Ints
  • e.g. doc["a"] = 5 sets the "a" key of a document to the BSON int64 5, and doc["a"] returns Int(5)

On 32-bit systems:

  • Int is encoded as a BSON int32
  • BSON int32s are read out of documents as Ints
  • BSON int64s are read out of documents as Int64s

On both systems, Int32 and Int64 are encoded to BSON int32 and BSON int64, respectively.

BSONNumber

To facilitate writing architecture-independent code (which is rare, since Swift support for 32-bit is extremely limited), we introduced the BSONNumber protocol, which all the numeric BSONValue types (Int32, Int64, Int, Double, and Decimal128) conform to. Conformance to this protocol allows conversion to any of the number types that BSON natively supports. However, the conversions will only return a value if the conversion is exact, and will return nil otherwise.

let a: BSONNumber = 5.2
a.int32Value // nil
a.doubleValue // Double(5.2)
       
let b: BSONNumber = 5.0
b.int32Value // int32(5)
b.doubleValue // Double(5.0)
   
let c: BSONNumber = Int32.max + 1
c.int32Value // nil
c.int64Value // Int64(2147483648)

// Example usage for when you know it's a number, but not what type of number it is and/or you don't care
let doc: Document = ["a": 5.0]
(doc["a"] as! BSONNumber).intValue // 5

New Types for Deprecated BSON Types

We've added new types for deprecated BSON types: Undefined, DBPointer, and Symbol. Previously, when extracted from a Document, values encoded as those types would be automatically converted to similar non-deprecated ones. Their types are now preserved.

bsonEquals added to BSONValue protocol

bsonEquals is now part of the BSONValue protocol. Statements that were previously written as bsonEquals(a, b) can now be written as a.bsonEquals(b). The old syntax is deprecated and will be removed in a future release.

Coding Strategies Introduced

We've introduced the concept of a Coding Strategy in this release, which allows the user to specify how certain values get encoded to and decoded from BSON using BSONEncoder / BSONDecoder. The provided strategies are heavily based on the encoding and decoding strategies used in Foundation's JSONEncoder/JSONDecoder, and are implemented to behave similarly. See the driver documentation (and Foundations docs) for information on how they can be used. An in-depth guide is forthcoming for usage in the driver.

let date = Date(timeIntervalSince1970: 1.5)
let codingOptions = BSONCoderOptions(dateCodingStrategy: .millisecondsSince1970)
let doc = try BSONEncoder(options: codingOptions).encode(["a": date]) // ["a": Int64(1500)]
try BSONDecoder(options: codingOptions).decode(DateWrapperA.self, from: doc).a.timeIntervalSince1970 // 1.5

Release Notes

Bug

  • [SWIFT-294] - TopologyDescription initializer doesn't clean up server descriptions array
  • [SWIFT-351] - Correctly encode strings with multi-byte UTF8 characters
  • [SWIFT-394] - Ensure all bson_ts are correctly cleaned up

New Feature

  • [SWIFT-276] - Implement workaround for Swift 5.0 byte alignment cap to enable Swift 5 support
  • [SWIFT-337] - Support setting of encoding/decoding strategies on client, database, and collection levels

Improvement

  • [SWIFT-144] - Update CRUD API errors to match the new hierarchy
  • [SWIFT-221] - Provide better consistency around Int usage with Documents
  • [SWIFT-268] - Store bson_oid_t in ObjectId rather than creating one each time we need it
  • [SWIFT-299] - Introduce new errors and error types
  • [SWIFT-300] - Convert InsertManyResult to BulkWriteResult when insertMany throws BulkWriteError
  • [SWIFT-301] - Convert invalidCollection, invalidClient, invalidUri, and invalidResponse errors to internalError or fatalError
  • [SWIFT-302] - Convert invalidCursor errors to commandErrors, logicErrors and invalidArgument errors
  • [SWIFT-303] - Convert bsonParseError to internalError
  • [SWIFT-304] - Convert bsonEncodeError, bsonDecodeError, typeError to new error types
  • [SWIFT-305] - Convert readPreferenceError to invalid argument or logic errors
  • [SWIFT-310] - Remove old errors
  • [SWIFT-313] - Move RegularExpression.nsRegularExpression logic into a new NSRegularExpression initializer
  • [SWIFT-331] - Throw an error when a non-BSONEncoder is used in encode(to:) for all BSONValue types that we own
  • [SWIFT-332] - Throw an error when non-BSONDecoder is used in init(from: decoder) for BSONValue types
  • [SWIFT-352] - Test round-tripping of BSON types with native representations using the BSON corpus data
  • [SWIFT-356] - Round trip Symbols, DBPointers, and Undefineds correctly
  • [SWIFT-358] - Don't require connectionString label in MongoClient initializer
  • [SWIFT-372] - Include bsonEquals as part of BSONValue protocol
  • [SWIFT-379] - Improve error message for type mismatches when decoding driver introduced BSON types
  • [SWIFT-384] - Provide an internal accessor for `bson_t`s length
  • [SWIFT-390] - Make bson pointer access explicit