All files / client createClient.js

96.55% Statements 28/29
85.71% Branches 18/21
100% Functions 7/7
96.55% Lines 28/29
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84                    15x     19x   19x 13x 13x         19x     26x   26x 24x     26x       26x   26x 5x   1x     1x   4x           1x 1x         1x       19x       19x 361x 361x   361x   361x 361x         19x       19x    
/* @flow */
 
import invariant from "invariant";
import deepAssign from "deep-assign";
import ApiMethod from "../api/ApiMethod";
import type { ClientApiMethodOptions, ClientMethod, ClientType } from "./types";
import type { ApiResult } from "../api/types";
import * as methods from "./methods";
import { isAuthMethod } from "../utils";
 
const defaultApiServer = "api.pcloud.com";
 
export default function createClient(token: string, type: ClientType = "oauth", useProxy: boolean = false) {
  invariant(["oauth", "pcloud"].indexOf(type) !== -1, "`type` must be either `oauth` or `pcloud`.");
 
  if (type === "oauth") {
    invariant(typeof token === "string", "`token` is required.");
    invariant(token.length, "`token` is required.");
  }
 
  // Local Params
  // apiServer, token, type
  let apiServer = defaultApiServer;
 
  function initialOptions(method: string) {
    let options = { apiServer: apiServer, params: {} };
 
    if (isAuthMethod(method) && token) {
      options.params["oauth" === type ? "access_token" : "auth"] = token;
    }
 
    return options;
  }
 
  function api(method: string, options?: ClientApiMethodOptions = {}): Promise<ApiResult> {
    let mergeOptions = deepAssign({}, initialOptions(method), options);
 
    return ApiMethod(method, mergeOptions).catch(error => {
      if (error.result === 500 && apiServer !== defaultApiServer) {
        // reset API server
        apiServer = defaultApiServer;
 
        // retry
        return api(method, options);
      } else {
        return Promise.reject(error);
      }
    });
  }
 
  function setupProxy(): Promise<string> {
    return api("getapiserver", {}).then((response: any) => {
      return (apiServer = response.api[0]);
    });
  }
 
  function setToken(newToken: string): void {
    token = newToken;
  }
 
  // client api for end users
  let client: any = { api, setupProxy };
 
  let pcloudMethod;
 
  for (let method in methods) {
    Eif (methods.hasOwnProperty(method)) {
      let baseMethod: ClientMethod = methods[method];
 
      pcloudMethod = baseMethod({ client, setToken, type }, type);
 
      Eif (typeof pcloudMethod === "function") {
        client[method] = pcloudMethod;
      }
    }
  }
 
  Iif (useProxy) {
    setupProxy();
  }
 
  return client;
}