Initial extraction from other project
This commit is contained in:
parent
81c4890897
commit
a54aa3ba0c
54
LICENSE
54
LICENSE
@ -1,21 +1,43 @@
|
|||||||
MIT License
|
This is a modified Apache License:
|
||||||
|
|
||||||
|
You are permitted to use, compile, execute, the code in this repository,
|
||||||
|
as long as this driver's protocol output is not sent over the SSL/TLS
|
||||||
|
protocol. You are prohibited from connecting this driver to Compose.IO
|
||||||
|
or to any other SSL/TLS endpoint without a commercial license.
|
||||||
|
|
||||||
|
To remove this limitation and permit usage over SSL/TLS, a commercial
|
||||||
|
license must be purchased. The commercial license permitting use over
|
||||||
|
SSL/TLS and Compose.IO is available from Bit Armory Inc and can
|
||||||
|
be purchased here:
|
||||||
|
|
||||||
|
https://www.bitarmory.com/payments/rethinkdb
|
||||||
|
|
||||||
|
Copyright 2010-2012 RethinkDB
|
||||||
|
|
||||||
|
Copyright (c) .NET Foundation. All rights reserved.
|
||||||
|
|
||||||
|
Copyright (c) Daniel Cannon.
|
||||||
|
|
||||||
|
Copyright (c) 2015 Bitly.
|
||||||
|
|
||||||
|
Copyright 2010-2014 MongoDB Inc.
|
||||||
|
|
||||||
|
Copyright (c) 2016 Bit Armory Inc.
|
||||||
|
|
||||||
|
Copyright (c) 2016 Brian Chavez
|
||||||
|
* http://github.com/bchavez
|
||||||
|
* http://bchavez.bitarmory.com
|
||||||
|
|
||||||
Copyright (c) 2017 Daniel J. Summers
|
Copyright (c) 2017 Daniel J. Summers
|
||||||
|
* http://github.com/danieljsummers
|
||||||
|
|
||||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
Licensed under the Apache License, Version 2.0 (the "License"); you may not use
|
||||||
of this software and associated documentation files (the "Software"), to deal
|
these files except in compliance with the License. You may obtain a copy of the
|
||||||
in the Software without restriction, including without limitation the rights
|
License at
|
||||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
||||||
copies of the Software, and to permit persons to whom the Software is
|
|
||||||
furnished to do so, subject to the following conditions:
|
|
||||||
|
|
||||||
The above copyright notice and this permission notice shall be included in all
|
http://www.apache.org/licenses/LICENSE-2.0
|
||||||
copies or substantial portions of the Software.
|
|
||||||
|
|
||||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
Unless required by applicable law or agreed to in writing, software distributed
|
||||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
|
||||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
CONDITIONS OF ANY KIND, either express or implied. See the License for the
|
||||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
specific language governing permissions and limitations under the License.
|
||||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
||||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
||||||
SOFTWARE.
|
|
67
README.md
67
README.md
@ -1,2 +1,69 @@
|
|||||||
# RethinkDb.Driver.FSharp
|
# RethinkDb.Driver.FSharp
|
||||||
Idiomatic F# extensions for the C# RethinkDB driver
|
Idiomatic F# extensions for the C# RethinkDB driver
|
||||||
|
|
||||||
|
## Licensing
|
||||||
|
|
||||||
|
While no specific additional license restrictions exist for this project, there are modifications to the Apache v2
|
||||||
|
license on this project's dependencies. Please see [the heading on the C# driver page][license] for details.
|
||||||
|
|
||||||
|
## Using
|
||||||
|
|
||||||
|
It is still early days on this project; however, AppVeyor CI provides a [NuGet feed][nuget] that builds packages for
|
||||||
|
each commit.
|
||||||
|
|
||||||
|
## Goals
|
||||||
|
|
||||||
|
The goal is to provide:
|
||||||
|
- A composable pipeline for creating ReQL statements:
|
||||||
|
|
||||||
|
```fsharp
|
||||||
|
/// string -> (IConnection -> Async<Post>)
|
||||||
|
let fetchPost (postId : string) =
|
||||||
|
fromDb "Blog"
|
||||||
|
|> table "Post"
|
||||||
|
|> get postId
|
||||||
|
|> asyncResult<Post>
|
||||||
|
```
|
||||||
|
|
||||||
|
- An F# domain-specific language (DSL) using a `rethink` computation expression:
|
||||||
|
|
||||||
|
```fsharp
|
||||||
|
/// string -> (IConnection -> Async<Post>)
|
||||||
|
let fetchPost (postId : string) =
|
||||||
|
rethink {
|
||||||
|
fromDb "Blog"
|
||||||
|
table "Post"
|
||||||
|
get postId
|
||||||
|
asyncResult<Post>
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
- A standard way to translate JSON into a strongly-typed configuration:
|
||||||
|
|
||||||
|
```fsharp
|
||||||
|
/// type: DataConfig
|
||||||
|
let config = DataConfig.fromJsonFile "data-config.json"
|
||||||
|
|
||||||
|
/// type: IConnection
|
||||||
|
let conn = config.Connect ()
|
||||||
|
|
||||||
|
/// type: Post (utilizing either example above)
|
||||||
|
let post = fetchPost "the-post-id" conn |> Async.RunSynchronously
|
||||||
|
```
|
||||||
|
|
||||||
|
- Only rename functions/methods where required
|
||||||
|
|
||||||
|
```fsharp
|
||||||
|
// Function names cannot be polymorphic the way object-oriented methods can, so filter's three overloads become
|
||||||
|
filter r.HashMap("age", 30)
|
||||||
|
// and
|
||||||
|
filterFunc (fun row -> row.["age"].Eq(30))
|
||||||
|
// and
|
||||||
|
filterJS "function (row) { return 30 == row['age'] }"
|
||||||
|
```
|
||||||
|
|
||||||
|
The composable pipeline and the JSON configuration are the early goals, as the computation expression will utilize the
|
||||||
|
same composition as those functions.
|
||||||
|
|
||||||
|
[license]: https://github.com/bchavez/RethinkDb.Driver#open-source-and-commercial-licensing
|
||||||
|
[nuget]: https://ci.appveyor.com/nuget/danieljsummers-rethinkdb-driver-fsharp
|
11
appveyor.yml
Normal file
11
appveyor.yml
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
os: Visual Studio 2017
|
||||||
|
|
||||||
|
build_script:
|
||||||
|
- cmd: dotnet restore src\RethinkDb.Driver.FSharp.fsproj
|
||||||
|
- cmd: dotnet build -v n src\RethinkDb.Driver.FSharp.fsproj
|
||||||
|
- cmd: dotnet pack src\RethinkDb.Driver.FSharp.fsproj -o %CD%\artifacts\nupkg
|
||||||
|
|
||||||
|
artifacts:
|
||||||
|
- path: artifacts\nupkg\*.nupkg
|
||||||
|
|
||||||
|
tests: off
|
95
src/RethinkDb.Driver.FSharp/Config.fs
Normal file
95
src/RethinkDb.Driver.FSharp/Config.fs
Normal file
@ -0,0 +1,95 @@
|
|||||||
|
namespace RethinkDb.Driver.FSharp
|
||||||
|
|
||||||
|
open Newtonsoft.Json.Linq
|
||||||
|
open RethinkDb.Driver
|
||||||
|
open RethinkDb.Driver.Net
|
||||||
|
|
||||||
|
/// Parameters for the RethinkDB configuration
|
||||||
|
type DataConfigParameter =
|
||||||
|
| Hostname of string
|
||||||
|
| Port of int
|
||||||
|
| User of string * string
|
||||||
|
| AuthKey of string
|
||||||
|
| Timeout of int
|
||||||
|
| Database of string
|
||||||
|
|
||||||
|
/// RethinDB configuration
|
||||||
|
type DataConfig =
|
||||||
|
{ Parameters : DataConfigParameter list }
|
||||||
|
with
|
||||||
|
static member empty =
|
||||||
|
{ Parameters = [] }
|
||||||
|
/// Create a RethinkDB connection
|
||||||
|
member this.CreateConnection () : IConnection =
|
||||||
|
let folder (builder : Connection.Builder) block =
|
||||||
|
match block with
|
||||||
|
| Hostname x -> builder.Hostname x
|
||||||
|
| Port x -> builder.Port x
|
||||||
|
| User (x, y) -> builder.User (x, y)
|
||||||
|
| AuthKey x -> builder.AuthKey x
|
||||||
|
| Timeout x -> builder.Timeout x
|
||||||
|
| Database x -> builder.Db x
|
||||||
|
let bldr =
|
||||||
|
this.Parameters
|
||||||
|
|> Seq.fold folder (RethinkDB.R.Connection ())
|
||||||
|
upcast bldr.Connect ()
|
||||||
|
/// The effective hostname
|
||||||
|
member this.Hostname =
|
||||||
|
match this.Parameters
|
||||||
|
|> List.tryPick (fun x -> match x with Hostname _ -> Some x | _ -> None) with
|
||||||
|
| Some (Hostname x) -> x
|
||||||
|
| _ -> RethinkDBConstants.DefaultHostname
|
||||||
|
/// The effective port
|
||||||
|
member this.Port =
|
||||||
|
match this.Parameters
|
||||||
|
|> List.tryPick (fun x -> match x with Port _ -> Some x | _ -> None) with
|
||||||
|
| Some (Port x) -> x
|
||||||
|
| _ -> RethinkDBConstants.DefaultPort
|
||||||
|
/// The effective connection timeout
|
||||||
|
member this.Timeout =
|
||||||
|
match this.Parameters
|
||||||
|
|> List.tryPick (fun x -> match x with Timeout _ -> Some x | _ -> None) with
|
||||||
|
| Some (Timeout x) -> x
|
||||||
|
| _ -> RethinkDBConstants.DefaultTimeout
|
||||||
|
/// The effective database
|
||||||
|
member this.Database =
|
||||||
|
match this.Parameters
|
||||||
|
|> List.tryPick (fun x -> match x with Database _ -> Some x | _ -> None) with
|
||||||
|
| Some (Database x) -> x
|
||||||
|
| _ -> RethinkDBConstants.DefaultDbName
|
||||||
|
/// Parse settings from JSON
|
||||||
|
///
|
||||||
|
/// A sample JSON object with all the possible properties filled in:
|
||||||
|
/// {
|
||||||
|
/// "hostname" : "my-host",
|
||||||
|
/// "port" : 12345,
|
||||||
|
/// "username" : "my-user-name",
|
||||||
|
/// "password" : "my-password",
|
||||||
|
/// "auth-key" : "my-auth-key",
|
||||||
|
/// "timeout" : 77,
|
||||||
|
/// "database" : "default-db"
|
||||||
|
/// }
|
||||||
|
///
|
||||||
|
/// None of these properties are required, and properties not matching any of the above listed ones will be ignored.
|
||||||
|
static member FromJson json =
|
||||||
|
let isNotNull = not << isNull
|
||||||
|
let parsed = JObject.Parse json
|
||||||
|
let config =
|
||||||
|
seq {
|
||||||
|
match parsed.["hostname"] with x when isNotNull x -> yield Hostname <| x.Value<string> () | _ -> ()
|
||||||
|
match parsed.["port"] with x when isNotNull x -> yield Port <| x.Value<int> () | _ -> ()
|
||||||
|
match parsed.["auth-key"] with x when isNotNull x -> yield AuthKey <| x.Value<string> () | _ -> ()
|
||||||
|
match parsed.["timeout"] with x when isNotNull x -> yield Timeout <| x.Value<int> () | _ -> ()
|
||||||
|
match parsed.["database"] with x when isNotNull x -> yield Database <| x.Value<string> () | _ -> ()
|
||||||
|
let userName = parsed.["username"]
|
||||||
|
let password = parsed.["password"]
|
||||||
|
match isNotNull userName && isNotNull password with
|
||||||
|
| true -> yield User (userName.Value<string> (), password.Value<string> ())
|
||||||
|
| _ -> ()
|
||||||
|
}
|
||||||
|
|> List.ofSeq
|
||||||
|
{ Parameters = config }
|
||||||
|
/// Parse settings from a JSON text file
|
||||||
|
///
|
||||||
|
/// See doc for FromJson for the expected JSON format.
|
||||||
|
static member FromJsonFile = System.IO.File.ReadAllText >> DataConfig.FromJson
|
80
src/RethinkDb.Driver.FSharp/Functions.fs
Normal file
80
src/RethinkDb.Driver.FSharp/Functions.fs
Normal file
@ -0,0 +1,80 @@
|
|||||||
|
[<AutoOpen>]
|
||||||
|
module RethinkDb.Driver.FSharp.Functions
|
||||||
|
|
||||||
|
open RethinkDb.Driver
|
||||||
|
|
||||||
|
let private r = RethinkDB.R
|
||||||
|
|
||||||
|
/// Get a connection builder that can be used to create one RethinkDB connection
|
||||||
|
let connection () =
|
||||||
|
r.Connection ()
|
||||||
|
|
||||||
|
/// Get the results of an expression
|
||||||
|
let asyncResult<'T> conn (expr : Ast.ReqlExpr) =
|
||||||
|
expr.RunResultAsync<'T> conn
|
||||||
|
|> Async.AwaitTask
|
||||||
|
|
||||||
|
/// Get the result of a non-select ReQL expression
|
||||||
|
let asyncReqlResult conn (expr : Ast.ReqlExpr) =
|
||||||
|
expr.RunResultAsync conn
|
||||||
|
|> Async.AwaitTask
|
||||||
|
|
||||||
|
/// Get a list of databases
|
||||||
|
let dbList conn =
|
||||||
|
r.DbList ()
|
||||||
|
|> asyncResult<string list> conn
|
||||||
|
|
||||||
|
/// Create a database
|
||||||
|
let dbCreate dbName conn =
|
||||||
|
r.DbCreate dbName
|
||||||
|
|> asyncReqlResult conn
|
||||||
|
|
||||||
|
/// Reference a database
|
||||||
|
let db dbName =
|
||||||
|
r.Db dbName
|
||||||
|
|
||||||
|
/// Reference the default database
|
||||||
|
let defaultDb =
|
||||||
|
(fun () -> r.Db ()) ()
|
||||||
|
|
||||||
|
/// Get a list of tables for the given database
|
||||||
|
let tableList conn (db : Ast.Db) =
|
||||||
|
db.TableList ()
|
||||||
|
|> asyncResult<string list> conn
|
||||||
|
|
||||||
|
/// Create a table in the given database
|
||||||
|
let tableCreate tableName conn (db : Ast.Db) =
|
||||||
|
db.TableCreate tableName
|
||||||
|
|> asyncReqlResult conn
|
||||||
|
|
||||||
|
/// Return all documents in a table (may be further refined)
|
||||||
|
let table tableName (db : Ast.Db) =
|
||||||
|
db.Table tableName
|
||||||
|
|
||||||
|
/// Return all documents in a table from the default database (may be further refined)
|
||||||
|
let fromTable tableName =
|
||||||
|
table tableName defaultDb
|
||||||
|
|
||||||
|
/// Get a list of indexes for the given table
|
||||||
|
let indexList conn (table : Ast.Table) =
|
||||||
|
table.IndexList ()
|
||||||
|
|> asyncResult<string list> conn
|
||||||
|
|
||||||
|
/// Create an index on the given table
|
||||||
|
let indexCreate indexName conn (table : Ast.Table) =
|
||||||
|
table.IndexCreate indexName
|
||||||
|
|> asyncReqlResult conn
|
||||||
|
|
||||||
|
/// Get a document by its primary key
|
||||||
|
let get documentId (table : Ast.Table) =
|
||||||
|
table.Get documentId
|
||||||
|
|
||||||
|
/// Get all documents matching keys in the given index
|
||||||
|
let getAll (ids : 'T seq) indexName (table : Ast.Table) =
|
||||||
|
table.GetAll(ids |> Array.ofSeq).OptArg("index", indexName)
|
||||||
|
|
||||||
|
|
||||||
|
/// Get a cursor with the results of an expression
|
||||||
|
let asyncCursor<'T> conn (expr : Ast.ReqlExpr) =
|
||||||
|
expr.RunCursorAsync<'T> conn
|
||||||
|
|> Async.AwaitTask
|
29
src/RethinkDb.Driver.FSharp/RethinkDb.Driver.FSharp.fsproj
Normal file
29
src/RethinkDb.Driver.FSharp/RethinkDb.Driver.FSharp.fsproj
Normal file
@ -0,0 +1,29 @@
|
|||||||
|
<Project Sdk="FSharp.NET.Sdk;Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<TargetFrameworks>net45;netstandard1.6</TargetFrameworks>
|
||||||
|
<Description>Idiomatic F# extentions to the official RethinkDB C# driver</Description>
|
||||||
|
<Authors>Daniel J. Summers</Authors>
|
||||||
|
<PackageLicenseUrl>https://github.com/danieljsummers/RethinkDb.Driver.FSharp/blob/master/LICENSE</PackageLicenseUrl>
|
||||||
|
<PackageProjectUrl>https://github.com/danieljsummers/RethinkDb.Driver.FSharp</PackageProjectUrl>
|
||||||
|
<!-- PackageIconUrl>https://github.com/danieljsummers/RethinkDb.Driver.FSharp/raw/master/icon/icon.png</PackageIconUrl -->
|
||||||
|
<PackageRequireLicenseAcceptance>false</PackageRequireLicenseAcceptance>
|
||||||
|
<PackageReleaseNotes>Alpha; use at your own risk</PackageReleaseNotes>
|
||||||
|
<Copyright>See LICENSE</Copyright>
|
||||||
|
<PackageTags>RethinkDB document F#</PackageTags>
|
||||||
|
<VersionPrefix>0.7.0</VersionPrefix>
|
||||||
|
<VersionSuffix>alpha-0001</VersionSuffix>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<Compile Include="Functions.fs" />
|
||||||
|
<Compile Include="Config.fs" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<PackageReference Include="FSharp.Core" Version="4.2.*" />
|
||||||
|
<PackageReference Include="FSharp.NET.Sdk" Version="1.0.*" PrivateAssets="All" />
|
||||||
|
<PackageReference Include="RethinkDb.Driver" Version="2.*" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
</Project>
|
Loading…
Reference in New Issue
Block a user