file-sharing-client-js
    TypeScript icon, indicating that this package has built-in type declarations

    1.0.85 • Public • Published

    About

    Client library for File Sharing Server based on fetch.

    Usage

    import {FileSharingClient, FileSharingClientOptions} from 'file-sharing-client-js';
    
    const fetch = window.fetch //in web or node-fetch in nodejs
    const clientOptions: FileSharingClientOptions = {
      authorization: 'value-of-signed-instance',
      fetch
    };
    const fileSharingClient = FileSharingClient.create(clientOptions);
    
    // Interacting with server
    try {
      const appSettings = await fileSharingClient.getAppSettings();
    } catch (e) {
      console.log('Error with code: ', e.errorCode);
    }
    

    Validation errros

    Server validates requests. When invalid request is made 400 HTTP error is handled by the library:

    it('invalid request', async () => {
      try {
        await fileSharingClient.viewFile({actions: [{libraryItemId: 'test'}]});
      } catch (e) {
        expect(e.errorCode).to.be.equal('InvalidRequest');
        expect(e.message).to.contain('is invalid');
      }
    });
    

    e.message holds explanation of the error that was sent by server.

    Enums

    For Enum fields you can import Enum constants or use strings that match constant name.

    Constants:

    import {wix} from 'file-sharing-client-js';
    
    displaySettings: {
      layoutOptions: wix.filesharing.api.v1.settings.LayoutOptions.LIST,
      textAlignment: wix.filesharing.api.v1.settings.TextAlignment.LEFT
    }
    

    Strings:

    import {wix} from 'file-sharing-client-js';
    
    displaySettings: {
      layoutOptions: 'LIST',
      textAlignment: 'LEFT'
    }
    

    Longs

    Big integers are represented as https://github.com/dcodeIO/long.js longs. Example is file size in bytes.

    Root Folder Id

    Root folder is a special folder. It is not physicaly stored anywhere. Root folder's parent is root folder itself. Each instance of file sharing can have different root folder id. Root folder id is provided in getAppSettings response.

    App Settings

    App settings entity contains all settings for site's or group's File Sharing TPA.

    {
      "uploadSettings":{
        "maxSizePerUploadMb":42,
        "allowVideoUploads": true
      },
      "downloadSettings":{
        "whoCanDownload":"ANYONE|MEMBERS_ONLY"
      },
      "favoriteSettings":{
        "isMembersAllowedToFavorite":true
      },
      "displaySettings":{
        "showFileOwnerName":true,
        "showSizeOfFiles":true,
        "showViewsCounter":true,
        "layoutOptions":"LIST|THUMBNAIL",
        "textAlignment":"LEFT|RIGHT",
        "showFileUploadDate":true,
        "showFavoritesCounter":true
      },
      "designSettings":{
        "fileIcon": "EXTENSION|CLASSIC|LINE",
        "buttonCornerRadius": 42,
        "dividerWidth": 42,
        "memberProfileDividerWidth": 42
      }
    }
    

    Updates existing or default app settings. Only keys present in json are updated (Object.keys).

    const settings = {
      uploadSettings: {
        maxSizePerUploadMb: 85,
      }
    };
    const {settings} = await fileSharingClient.updateAppSettings(settings);
    

    Get default or existing settings:

    const {settings, rootFolderId} = await fileSharingClient.getAppSettings();
    

    Errors

    Library Items

    Main domain entity is Library Item. Library Item can be either Folder or File.

    Library Item Entity
    {
      id: "uuid",
      name: "string",
      createdBy: "uuid",
      createdByName: "string", // Not always present
      createdAt: "Date object",
      parentFolderId: "uuid",
      path: [{
        id: "uuid",
        name: "folder name"
      }],
      isFavorited: true,
      timesFavorited: 42,
      uniqueViews: 42,
      isViewed: true,
      // When file item is a file
      fileFields: {
        extension: "string", //lowercase without dot "pdf", "jpg", etc.
        sizeInBytes: "int"
      },
    
      // When file item is a folder
      folderFields: {
        childrenCount: "int",
        lastModified: "Date object"
      }
    }
    
    Folder creation

    Creates new folder if it doesn't exist with same name.

    const {folderId} = await fileSharingClient.createFolder({
      action: {
        name: "string",
        parentFolderId: "uuid"; //Optional. To create under root folder send null or undefined
      }
    });
    
    Query library items

    When no filters specified all files sorted by its ID is returned until the limit is reached.

    const {libraryItems, metaData} = await fileSharingClient.queryLibraryItems({
      // Each filtering field is connected using logical AND.
      filter: {
        // Gets items with direct parent from this list.
        parentLibraryItemIds: [],
        // Gets all items that are descendants of given folder
        descendantsOfFolderId: "string",
        // Gets all items where name contains given string or is uploaded by matching user
        search: "string",
        // Gets all favorited items by current user
        filterFavoritedByCallingUser: "boolean",
        // Gets all items created by specified users
        createdBy: [],
        // Gets only files or folders. Empty means both.
        libraryItemTypes: [FILE, FOLDER]
      },
      sort: {
        sortBy: "NATURAL|CREATED_AT|NAME|TYPE|TIMES_FAVORITED|UNIQUE_VIEWS|LAST_MODIFIED",
        orientation: "DESC|ASC"
      },
      paging: {
        cursor: "string" //Optional. When unspecified will return first page until limit.
        limit: "number" //Optional. Limited to max 100.
      };
    });
    
    // Use next_cursor to fetch additional page. null means no more pages.
    // Filtering and sorting is encoded inside cursor.
    // Cursor takes precedence over given `filter` and `sorting` parameters
    const { nextCursor } = metaData;
    
    Query folder library items

    Get library items for given folders. Defaults to root folder when filter is unspecified.

    Response is identical to queryLibraryItems.

    const {libraryItems, metadata} = await fileSharingClient.queryLibraryFolderItems({
      filter: {
        parentLibraryItemIds: [] // Defaults to Root folder when empty or unspecified
      },
      sort: {}, // Same as in queryLibraryItems
      paging: {} // Same as in queryLibraryItems
    });
    
    Get Library items by id

    If it is not found it is ommited from response.

    const response = await fileSharingClient.getLibraryItemsById({libraryItemIds: [folderId]});
    expect(response.libraryItems).to.not.be.empty;
    
    Get Folder Tree

    rootLibraryItemId is optional. When given only tree from given folder will be returned.

    const response = await fileSharingClient.getFolderTree({rootLibraryItemId: '00000000-0000-0000-0000-000000000000'});
    expect(response).to.deep.equal({
      folderTree: {
        folderId: '00000000-0000-0000-0000-000000000000',
        name: '/',
        subfolders: []
      }
    });
    
    Upload file

    File upload consits of 3 phases:

    • start upload by getting upload url
    • upload to upload url
    • callback with upload response

    You can initiate multiple file uploads with single request:

    const response = await fileSharingClient.startFileUpload({
      actions: [{
        name: 'test.png',
        sizeInBytes: 123,
        parentFolderId: '00000000-0000-0000-0000-000000000000',
        actionId: 'unique_for_this_request'
      }]
    });
    expect(response).to.be.deep.equal({
      urls: [{
        url: 'uploadUrl',
        requestParameters: {
          parent_folder_id: 'uploadParentFolderId',
          upload_token: 'uploadToken'
        },
        actionId: 'success1'
      }],
      failures: [{
        fileName: 'test.png',
        fileExtensionNotSupported: {
          extension: 'png'
        },
        fileTooBig: {
          size: 42,
          maxSize: 41
        },
        actionId: 'failure1'
      }]
    });
    

    You should not care what is in requestParameters. Just map it to FormData when performing upload.

    Example of upload from browser:

    <html>
      <body>
        <script>
    
          const uploadUrl = 'urlFrom_startFileUpload';
          const requestParameters = {}; // From startFileUpload
    
          async function uploadFile(e) {
            const file = e.elements[0].files[0];
            console.log('fileName', file.nane); //This name should be provided to startFileUpload, completeFileUpload
    
            //Populate form data with request parameters as is
            const formData = new FormData(e);
            Object.keys(requestParameters).forEach(key => formData.append(key, requestParameters[key]))
    
            const response = await fetch(uploadUrl, {
              method: 'POST',
              body: formData,
            });
            // this response must be provded to completeFileUpload
            console.log(await response.text());
          }
        </script>
    
        <form id="upload-form" enctype="multipart/form-data" action="" method="post" target="upload-result" onsubmit="uploadFile(this)">
            <input id="file" name="file" type="file" accept="image/*">
            <input id="submit" type="submit">
        </form>
      </body>
    </html>
    

    Complete upload by providing uploadResponse:

    const response = await fileSharingClient.completeFileUpload({
      actions: [{
        parentFolderId: '00000000-0000-0000-0000-000000000000',
        uploadResponse: 'responseFromUploadUrl',
        actionId: 'unique_for_this_request'
      }]
    });
    
    expect(response).to.be.deep.equal({
      libraryItems: [{
        id: 'cfbeadb5-f75c-4046-a7a1-7b259f7ae382',
        name: 'file.png',
        createdBy: 'cfbeadb5-f75c-4046-a7a1-7b259f7ae382',
        createdByName: 'test',
        createdAt: new Date('1970-01-01T00:00:00.000Z'),
        parentFolderId: 'cfbeadb5-f75c-4046-a7a1-7b259f7ae382',
        path: [],
        isFavorited: true,
        timesFavorited: 42,
        uniqueViews: 42,
        isViewed: true,
        fileFields: {
          extension: 'png',
          sizeInBytes: 42
        }
      }],
      failures: [{
        fileName: 'test.png',
        fileTooBig: {
          size: 42,
          maxSize: 41
        },
        videoFilesForbidden: {},
        actionId: 'failure1'
      }]
    });
    

    Complete upload responds with newly created library items. You can complete upload of multiple files with single request.

    Errors

    UploadedFileNotFound, FileTooBig

    { errorCode: 'UploadedFileNotFound' }

    Downloading

    Same endpoint can be used to download:

    • single file: by probiding single id
    • multiple files: by providing multiple file ids
    • folder: by providing folder id

    When download is invoked with single file id it would return url that would download that file. Browser will start file download because url respons with header Content-Disposition: attachment.

    const response = await fileSharingClient.download({
      action: {
        libraryItemIds: ['cfbeadb5-f75c-4046-a7a1-7b259f7ae382']
      }
    });
    expect(response).to.be.deep.equal({url: 'http://testkit.download.com', isArchive: false});
    
    View file

    Returns url that responds with a file and Content-Disposition: inline

    const response = await fileSharingClient.viewFile({
      actions: [{
        libraryItemId: 'cfbeadb5-f75c-4046-a7a1-7b259f7ae382'
      }]
    });
    expect(response).to.deep.equal({
      urls: [{
        libraryItemId: 'cfbeadb5-f75c-4046-a7a1-7b259f7ae382',
        url : 'view-url'
      }]
    });
    
    
    View folder

    View folder increments folder view counts

    const response = await fileSharingClient.viewFolder({
      actions: [{
        libraryItemId: 'cfbeadb5-f75c-4046-a7a1-7b259f7ae382'
      }]
    });
    expect(response).to.deep.equal({});
    
    Favorite file or folder

    Marks file or folder as favorite

    const response = await fileSharingClient.favorite({
      actions: [{
        libraryItemId: 'cfbeadb5-f75c-4046-a7a1-7b259f7ae382',
        isFavorite: true
      }]
    });
    expect(response).to.deep.equal({});
    
    Rename file or folder

    parentFolderId is optinal. Specifying zero UUID or undefined yields same behavior.

    const response = await fileSharingClient.rename({
      actions: [{
        libraryItemId: 'cfbeadb5-f75c-4046-a7a1-7b259f7ae382', // File or Folder id
        newName: 'test',
        parentFolderId: '00000000-0000-0000-0000-000000000000'
      }]
    });
    expect(response).to.deep.equal({});
    
    Move file or folder

    To move file or folder just specify its id and new parent. When currentParentFolderId is null Root is assumed.

    const response = await fileSharingClient.move({
      actions: [{
        libraryItemId: 'cfbeadb5-f75c-4046-a7a1-7b259f7ae382',
        newParentFolderId: 'test',
        currentParentFolderId: '00000000-0000-0000-0000-000000000000'
      }]
    });
    expect(response).to.deep.equal({});
    
    Delete file or folder

    Deletes file or folder

    const response = await fileSharingClient.delete({
      actions: [{
        libraryItemIds: ['cfbeadb5-f75c-4046-a7a1-7b259f7ae382'],
        parentFolderId: '00000000-0000-0000-0000-000000000000'
      }]
    });
    expect(response).to.deep.equal({});
    
    Share file or folder

    Currently share is implemented as url shortener without any file/folder context. It is responsible to prepend correct site domain to given path

    const response = await fileSharingClient.share({
      urlPath: 'file-sharing-dev/file-sharing-dev/00000000-0000-0000-0000-000000000000'
    });
    expect(response).to.deep.equal({url: 'http://wix.to/testing'});
    
    Roles and Permissions
    Allowed actions

    Provides actions that are available to user. Some actions like UPLOAD_FILE, CREATE_FOLDER means that this action is available in the context of provided parent. When no ids are passed actions for root folder is resolved.

    const response = await fileSharingClient.listAllowedActions({
      libraryItemIds: ['00000000-0000-0000-0000-000000000000']
    });
    expect(response).to.deep.equal({
      allMembersActions: ['CREATE_FOLDER', 'UPLOAD_FILE'],
      allowedActions: ['RENAME', 'FAVORITE'],
      libraryItemAllowedActions: [{
        allowedActions: ['MOVE', 'DELETE'],
        libraryItemId: 'cfbeadb5-f75c-4046-a7a1-7b259f7ae382'
      }]
    });
    
    Assign permissions
    await fileSharingClient.assignPermissions({
      actions: [
        {
          permission: 'UPLOAD_FILE',
          roleId: '00000000-0000-0000-0000-000000000000'
        }
    ]});
    
    Remove permissions
    await fileSharingClient.removePermissions({
      actions: [
        {
          permission: 'CREATE_FOLDER',
          roleId: '00000000-0000-0000-0000-000000000000'
        }
    ]});
    
    List roles with permission
    const {roles} = await fileSharingClient.listRoles({
      permissions: ['CREATE_FOLDER', 'UPLOAD_FILE']
    });
    
    const {id, name, permissions, roleType} = roles[0];
    

    When permissions array is empty then role has no file sharing permission assigned.

    To fetch roles that have specific permission assigned use permissions filter.

    To fetch all roles omit permissions filter (null or empty array).

    List roles for current user

    Lists current roles assigned to requesting user

    const response = await fileSharingClient.listCurrentUserRoles();
    expect(response).to.deep.equal([
      {
        id: '00000000-0000-0000-0000-000000000000',
        name: 'Admin',
        roleType: 'ADMINS'
      },
      {
        id: '00000000-0000-0000-0000-000000000001',
        name: 'All Members',
        roleType: 'ALL_MEMBERS'
      },
      {
        id: '548c837e-40b4-46b4-8436-27f5b12d5548',
        name: 'Some custom role',
        roleType: 'CUSTOM'
      }
    ]);
    
    
    Role Entity
    {
      id: "uuid",
      name: "user given name of a role",
      permissions: [
        'CREATE_FOLDER', 'UPLOAD_FILE', 'MODERATE'
      ],
      roleType: "ALL_MEMBERS|ADMINS|CUSTOM"
    }
    

    Keywords

    none

    Install

    npm i file-sharing-client-js

    DownloadsWeekly Downloads

    0

    Version

    1.0.85

    License

    MIT

    Unpacked Size

    603 kB

    Total Files

    20

    Last publish

    Collaborators

    • wix-ci
    • wix-ambassador
    • shahata
    • netanelgilad
    • wix-ci-publisher
    • wix-bi-publisher