anchor.diff:  open HttpListenerHelper
   open Fake.SshRsaModule
   
  +/// Authentication token received from a successful login
   type AuthToken = 
       | AuthToken of Guid
   
  -let mutable private authToken : Guid option = None
  +let mutable private authToken : AuthToken option = None
   
   /// A http response type.
   type Response = 
  
positive.code: let getAllReleasesFor server appname = 
      if String.IsNullOrEmpty(appname) then server + "/deployments/"
      else server + "/deployments/" + appname + "/"
      |> get (Json.deserialize<DeploymentResponse>)
      |> wrapFailure
  
  /// Returns all releases from the given server.
  let getAllReleases server = getAllReleasesFor server null
  
  /// Posts a deployment package to the given URL.
  let postDeploymentPackage url packageFileName args = post url packageFileName args |> wrapFailure
  
  /// Posts a deployment package to the given URL, executes the script inside it with given arguments and handles the response.
  let DeployPackageWithArgs url packageFileName args =
      match postDeploymentPackage url packageFileName args with
      | Success _ -> tracefn "Deployment of %s successful" packageFileName
      | Failure exn -> failwithf "Deployment of %A failed\r\n%s" packageFileName (buildExceptionString exn)
      | response -> failwithf "Deployment of %A failed\r\n%A" packageFileName response
  
  /// Posts a deployment package to the given URL and handles the response.
  let DeployPackage url packageFileName = DeployPackageWithArgs url packageFileName [||]
  
  /// Deprecated, use DeployPackage
  
negative.code:     { Name : string
        Version : string }
  
  let private buildExceptionString (r : Response) = 
      let msgs = 
          r.Messages
          |> Seq.map (fun m -> sprintf "  %s %s" (m.Timestamp.ToString("yyyy-MM-dd hh::mm:ss.fff")) m.Message)
          |> fun arr -> String.Join("\r\n", arr)
      sprintf "%O\r\n\r\nDeploy messages\r\n{\r\n%s\r\n}\r\n" r.Exception msgs
  
  /// Authenticate against the given server with the given userId and private key
  let authenticate server userId serverpathToPrivateKeyFile passwordForPrivateKey = 
      let privateKey = loadPrivateKey serverpathToPrivateKeyFile passwordForPrivateKey
      let challenge = REST.ExecuteGetCommand null null (server + "/login/" + userId)
      
      let signature = 
          challenge
          |> Convert.FromBase64String
          |> privateKey.Sign
          |> Convert.ToBase64String
      
      let postData = 
          sprintf "challenge=%s&signature=%s" (HttpUtility.UrlEncode challenge) (HttpUtility.UrlEncode signature)
      let response = REST.ExecutePost (server + "/login") "x" "x" postData
      authToken <- response.Trim([| '"' |])
                   |> Guid.Parse
                   |> AuthToken
                   |> Some
      authToken
  
  /// Returns all releases of the given app from the given server.
  let getReleasesFor server appname status = 
      if String.IsNullOrEmpty(appname) then server + "/deployments?status=" + status
      else server + "/deployments/" + appname + "?status=" + status
      |> get defaultTimeout (Json.deserialize<DeploymentResponse>)
  
  /// Performs a rollback of the given app on the server.
  let rollbackTo server appname version = 
      put (server + "/deployments/" + appname + "?version=" + version) [||] defaultTimeout |> wrapFailure
  
  /// Returns all active releases from the given server.
  let getAllActiveReleases server = getReleasesFor server null "active" |> wrapFailure
  