4.4.7 • Published 4 years ago

xero-node2 v4.4.7

Weekly downloads
3
License
MIT
Repository
github
Last release
4 years ago

Fork of xero-node library

xero-node

npm

Release of SDK with oAuth 2 support

Version 4.x of Xero NodeJS SDK only supports oAuth2 authentication and the following API sets.

  • accounting

Bank feeds support in OAuth 2

An early release in a separate package is availalbe bank feeds API.

Looking for OAuth 1.0a support?

npm package

We've moved this code into the oauth1 branch.

Getting Started

Create a Xero App

Follow these steps to create your Xero app

  • Create a free Xero user account (if you don't have one)
  • Login to Xero developer center
  • Click "Try oAuth2" link
  • Enter your App name, company url, privacy policy url.
  • Enter the redirect URI (this is your callback url - localhost, etc)
  • Agree to terms and condition and click "Create App".
  • Click "Generate a secret" button.
  • Copy your client id and client secret and save for use later.
  • Click the "Save" button. You secret is now hidden.

Repo Context & Contributing

This SDK's functionality is majority generated from our OpenAPISpec. The exception is the src/xeroClient.ts which contains the typescript that is unique to this repository. Contributions are welcome but please keep in mind that majority of SDK is auto-generated from the OpenAPISpec. We try to get changes in that projects to be released on a reasonable cadence.

Read more about our process in maintaining our suite of SDK's

Testing

We are working to build out a more robust test suite, and currently just have tests setup for our xeroClient.ts - PR's will now run against a CI build - and as we add more tests to this project community collaboration will be easier to incorporate.

npm test

Authentication

We use OAuth2.0 to authenticate requests against our API. Each API call will need to have a valid token populated on the API client to succeed. In a tokenSet will be an access_token which lasts for 30 minutes, and a refresh_token which lasts for 30 days. If you don't want to require your users to re-authenticate each time you want to call the API on their behalf, you will need a datastore for these tokens and will be required to refresh the tokens at least once per 30 days to avoid expiration. The offline_access scope is required for refresh tokens to work.

In Xero a user can belong to multiple organisations. Tokens are ultimately associated with a Xero user, who can belong to multiple tenants/organisations. If your user 'Allows Access' to multiple organisations, be hyper aware of which tenantId you are passing to each function.


Step 1: Initialize the XeroClient, and redirect user to xero auth flow

Step 2: Call apiCallback to get your tokenSet

Step 3: Call updateTenats to populate additional tenant data


Step 1

  • Configure client and generate Authorization URL
  • Choose XeroAPI Scopes based on the access you need
  • initialize() the client to set up the 'openid-client'
  • Build the consentUrl
  • Redirect to auth flow
const port = process.env.PORT || 3000

const xero = new XeroClient({
  clientId: 'YOUR_CLIENT_ID',
  clientSecret: 'YOUR_CLIENT_SECRET',
  redirectUris: [`http://localhost:${port}/callback`],
  scopes: 'openid profile email accounting.transactions offline_access'.split(" ")
});

await xero.initialize();

let consentUrl = await xero.buildConsentUrl();

res.redirect(consentUrl);

Step 2

Call apiCallback function with the response url which returns a tokenSet you can save in your datastore for future calls.

The tokenSet can also be accessed from the client as xero.readTokenSet().

const tokenSet = await xero.apiCallback(req.url);

The tokenSet will contain your access_token and refresh_token as well as other information regarding your connection.

{
  id_token: 'eyJhxxxx.yyy',
  access_token: 'eyJxxx.yyy.zzz',
  expires_at: 1231231234,
  token_type: 'Bearer',
  refresh_token: 'xxxyyyyzzz',
  scope: 'openid profile email accounting.settings accounting.reports.read accounting.journals.read accounting.contacts accounting.attachments accounting.transactions offline_access',
  session_state: 'xxx.yyy'
}

Step 3 (convenience step)

Populate the XeroClient's active tenant data

For most integrations you will always want to display the org name and additional metadata about the connected org. The /connections endpoint does not currently serialize that data so requires developers to make additional api calls for each org that your user connects to surface that information.

The updatedTenants function will query & nest the additional orgData results in your xeroClient under each connection/tenant object and return the array of tenants.

const tenants = await xero.updateTenants()

console.log(tenants || xero.tenants)
[
  {
    id: 'xxx-yyy-zzz-xxx-yyy',
    tenantId: 'xxx-yyy-zzz-xxx-yyy',
    tenantType: 'ORGANISATION',
    createdDateUtc: 'UTC-DateString',
    updatedDateUtc: 'UTC-DateString',
    orgData: {
      organisationID: 'xxx-yyy-zzz-xxx-yyy',
      name: 'My first org',
      version: 'US',
      shortCode: '!2h37s',
      ...
    }
  },
  {
    id: 'xxx-yyy-zzz-xxx-yyy',
    tenantId: 'xxx-yyy-zzz-xxx-yyy',
    tenantType: 'ORGANISATION',
    createdDateUtc: 'UTC-DateString',
    updatedDateUtc: 'UTC-DateString',
    orgData: {
      organisationID: 'xxx-yyy-zzz-xxx-yyy',
      name: 'My second org',
      version: 'AUS',
      shortCode: '!yrcgp',
      ...
    }
  }
]

Making offline_access calls

Once you have a valid token saved you can set the token on the client without going through the callback by calling setTokenSet.

For example - once a user authenticates you can refresh the token (which will also set the new token on the client) to make authorized api calls.

const tokenSet = getTokenFromDatabase(userId) // example function name

await xero.setTokenSet(tokenSet)

// you can call this to fetch/set your connected tenant data on your client, or you could also store this information in a database
await xero.updateTenants()

await xero.accountingApi.getInvoices(xero.tenants[0].tenantId)

SDK Documentation

Basics

const activeTenantId = xero.tenants[0].tenantId

const getOrgs = await xero.accountingApi.getOrganisations(activeTenantId)
const orgCountry= getOrgs.body.organisations[0].countryCode

const contactsResponse = await xero.accountingApi.getContacts(activeTenantId)
const contactId = getContactsResponse.body.contacts[0].contactID

---
import { XeroClient, Invoice } from "xero-node";

const invoices = {
  invoices: [
    {
      type: Invoice.TypeEnum.ACCREC,
      contact: {
        contactID: contactId
      },
      lineItems: [
        {
          description: "Acme Tires",
          quantity: 2.0,
          unitAmount: 20.0,
          accountCode: "500",
          taxType: "NONE",
          lineAmount: 40.0
        }
      ],
      date: "2019-03-11",
      dueDate: "2018-12-10",
      reference: "Website Design",
      status: Invoice.StatusEnum.AUTHORISED
    }
  ]
};

const createdInvoice = await xero.accountingApi.createInvoices(activeTenantId, invoices)

Sample App

For more robust examples in how to utilize our accounting api we have (roughly) every single endpoint mapped out with an example in our sample app - complete with showing the Xero data dependencies required for interaction with many objects ( ie. types, assoc. accounts, tax types, date formats).

Just visit the repo https://github.com/XeroAPI/xero-node-oauth2-app configure your credentials & get started.

Other Helper functions

// xero.tenants
xero.tenants

// buildConsentUrl()
await xero.buildConsentUrl()

// readTokenSet()
const tokenSet = await xero.readTokenSet();

// tokenSet.expired()
if (tokenSet.expired()) {
  // refresh etc.
}

// refreshToken()
const validTokenSet = await xero.refreshToken()

// refreshTokenUsingTokenSet()
await xero.refreshTokenUsingTokenSet(tokenSet)

// disconnect()
await xero.disconnect(xero.tenants[0].id)

// readIdTokenClaims()
await xero.readIdTokenClaims()

// readTokenSet()
await xero.readTokenSet()

// setTokenSet(tokenSet)
const tokenSet = await xero.readTokenSet()
await xero.setTokenSet(tokenSet)
4.4.7

4 years ago

4.4.6

4 years ago

4.4.4

4 years ago

4.4.5

4 years ago