In order to be able to use our FileApi you have to login with a valid user. (See example below)

  

public class loginRequest 

  {

        public string Useremail; // The users mail

        public string Password; // The users password

  }


First you have to get the user’s primaryDomain (See example below)

if the return value is null you should handle this (if null the server could not find the user)


private string GetPrimaryDomain(loginRequest loginRequest)

        {

            string siteString = Global.GlobalUrl+"/getuserdomain.aspx";

            using (WebClient client = new WebClient ())

            {

                client.Headers["useremail"] = loginRequest.Useremail;

                var globalResponse = client.DownloadString(siteString);

                if (globalResponse.StartsWith(loginRequest.Useremail))

                {

                    string primaryDomain = globalResponse.Replace(loginRequest.Useremail + ",", "");

                    return primaryDomain;

                }

                else

                {

                  return null;

                }

            }

        }


After you have the primary domain you need to login on that domain

string url = String.Format("https://clientgateway.{0}/Login2.aspx", primaryDomain);

public void LoginToDomain(loginRequest loginRequest, string url)

        {

            using (WebClient web = new WebClient())

            {

                web.Headers.Add("useremail", loginRequest.Useremail);

                web.Headers.Add("password2", Convert.ToBase64String(Encoding.UTF8.GetBytes(loginRequest.Password)));

                web.Headers.Add("deviceid", string.Empty);

                web.Headers.Add("devicename", "CustomImplementation"); // This is just a string you could call it custom implementation

                web.Headers.Add("devicetype", DeviceType.WebClient.ToString()); //Enum that is called DeviceType see list of classes for details

                web.Headers.Add("deviceos", string.Format("{0} {1}", "", "")); //This is the machines OS, example 0="Windows" 1="10"

                web.Headers.Add("ip", ""); //Ip of the requestor

                string jsonResponse = string.Empty;

                Stream data = web.OpenRead(url);

                StreamReader reader = new StreamReader(data);

                jsonResponse = reader.ReadToEnd();

                data.Close();

                reader.Close();

             

                GlobalLoginResponce globalLoginResponce = JsonConvert.DeserializeObject<GlobalLoginResponce>(jsonResponse);

                if (globalLoginResponce.ErrorCode == "U100")

                {

                   //Success

                   //You should save the globalLoginResponce since you will need this later.

                }                 

            }             

        }



  After you have saved the globalLoginResponce you have to login on every domain

  //The userDomains are part of the GlobalLoginResponce (remember the primary domain is also a userdomain)

  //After you have logged in on each domian you should have a list of shares and be ready to upload files

private void GateWayLogin(UserDomain userDomain, string userEmail)

        {

           

            string uriString = "";

            uriString = string.Format("https://clientgateway.{0}/ClientLogin.aspx?userEmail={1}&token={2}",

                                           userDomain.Domain.Url,

                                           userEmail),

                                           userDomain.UserDomainToken);

            try

            {

                string jsonResponse = string.Empty;

                using (CookieAwareWebClient web = new CookieAwareWebClient())

                {

                    web.Timeout = 5;

                    using (Stream data = web.OpenRead(uriString))

                    {

                        using (StreamReader reader = new StreamReader(data))

                        {

                            jsonResponse = reader.ReadToEnd();

                        }

                    }

                }

                //ClientLoginResponce See list of classes for details

                var clientLoginResponse = JsonConvert.DeserializeObject<ClientLoginResponce>(jsonResponse);

   

                //ManagedShare See list of classes for details

                foreach (ManagedShare managedShare in clientLoginResponse.ManagedShares)

                {

                    managedShare.GateWayUrl = userDomain.Domain.Url;

                    managedShare.ShareAcl.AclToken = HttpUtility.UrlDecode(managedShare.ShareAcl.AclToken);

                }

            }

            catch (Exception e)

            {

                //Should handle domains that are not responding

            }

        }



API url - https://filecache[number].[domain]/clientfileapi.ashx


overview

This part of the api allows the client application to send file system modification events

(create, delete, rename, update, etc.), upload and download files. It has 4 methods (actions): fileEvent, upload, download, read.


pre-conditions

To be able to call this API, you need to have a valid AclToken for the share you are applying changes on.


methods


1. Sending file event


request headers:

request parameters:

action: fileEvent

Request: JSON string that represents the .NET class defined below. You can send the request data in the HTTP request body:


public class FileJournalEvent

    {

        public string TransmitId { get; set; } //guid string, should be generated by client application

        public string UserOrigin { get; set; } // use name

        public ClientJournalEventType ClientJournalEventType { get; set; } // file event type (see enumeration bellow)

        public long TransmitDate { get; set; } //.NET DateTime UTC tick for time of transaction

        public RfVirtualFile RfVirtualFile { get; set; } // updated file metadata

        public string ShareToken { get; set; } //share AclToken

        public string DeviceId { get; set; } // current device Id

    }


ClientJournalEventType enumeration

0 Create

1 Delete,

2 Rename,

3 Update,

4 FileAttributes,

5 CatchUp,

6 Duplicate,

7 ConflictNewVersion,

8 FileNotPressent,

9 IgnoreDelete,

10 RenameConflict,

11 Recover,

12 Restore


Response structure


response is a JSON string that represents serialized object of next .NET class:

    public class FileJournalResponse

    {

        public string TransmitId { get; set; } // request transmit Id

        public string TransmitToken { get; set; } // transmit token, generated on server side

        public FileResponseCode ResponseCode { get; set; } // response codes (see enumeration bellow)

        // FilePosition  position of already uploaded file (for Create/Update events only, in case if previous upload attempt failed)

        public long FilePosition { get; set; } 

        public string UploadUrl { get; set; } filecache url

        public RfVirtualFile RfVirtualFile { get; set; } // file metadata, maybe modified by server

        // file journal event to be applied. Value is present in case of duplicates, conflicts, etc - should be null in all other cases.

        public FileJournalEvent FileJournalEvent { get; set; } 

        public ACLToken ShareToken { get; set; } // deserialized share ACL token

    }


 FileResponseCode enumeration:

0 DeniedAccess

1 Success

2 Conflict

3 Duplicate

4 NoRequest

5 NotYetImplemented

6 InsufficientData

7 AlreadyExist

8 FailedTalkingToServer

9 IgnoreDelete

10 EntityNotFound


2. File upload


File upload is done by chunks. Chunk size is chosen by client application.

Before to start upload file you need to send create/update file event request (see above) and proceed with the upload only if response code is “Success”. On each successfully uploaded chunk servers returns response with Success code, after all chunks are sucessfully uploaded (it is validated with the file metadata provided with file event request) response code should be “Done”.


request headers:

token : transmitToken from file event request

position : starting position of current chunk (number of first byte)

size : size of current chunk (number of bytes)

hash : md5 hash string of current chunk (for validation), hex-bytes separated by hyphen

(example - D0-53-74-DC-38-1D-9B-52-80-64-46-A7-1C-8E-79-B1)

request body - binary data, chunk content

response

response is a JSON string that represents serialized object of next .NET class


public class FileChunkUploadResponse

{

        public long Position { get; set; } // (not used - should be removed?)

        public FileChunkUploadResponseCode ResponseCode { get; set; } // operation response code (see enumeration bellow)

        public FileJournalEvent FileJournalEvent { get; set; } // final file event applied to file database (generated or modified by domain master)

 }


chunk upload response codes (FileChunkUploadResponseCode enumeration):

0 - Success, current chunk was successfully uploaded

1 - Failed, current chunk was failed to uploaded (means that all previously uploaded data are successfully stored and you can start again from the failed chunk itself)

2 - Done, file is fully uploaded (last chunk was just finished and changes are applied) - in this case response object should also contain FileJournalEvent

3 - FileFailed, file was failed to uploaded. (means that all data were lost or corrupted so you have to upload the whole file again)


3. Download

This method allows client application to download necessary file. To be able to download file you should have a valid share token.

request headers:

shareToken :share acl token, string (see pre-conditions above)

userOrigin : user name, string


request parameters:

action : download

file : file upload name, string

shareId : id of file’s share, giud string

position: starting position (if file was already partially downloaded)


response - file binary data

service returns NotFound http status (404) if file is not found on FileCache


4. Read

This method allows client application to read a chunk from the file. To be able to read a chunk you should have a valid share token.

request headers:

shareToken :share acl token, string (see pre-conditions above)

userOrigin : user name, string


request parameters:

action : read

file : file upload name, string

shareId : id of file’s share, giud string

position : starting position (number of first byte)

count : number of bytes to read


response - chunk binary data

service returns NotFound http status (404) if file is not found on FileCache