Research
Security News
Malicious npm Packages Inject SSH Backdoors via Typosquatted Libraries
Socket’s threat research team has detected six malicious npm packages typosquatting popular libraries to insert SSH backdoors.
timekit-sdk
Advanced tools
Make API calls to Timekit with our easy-to-use JavaScript SDK. It supports all our endpoints as documented on https://reference.timekit.io/.
Visit timekit.io to learn more and don't hesitate to contact Lasse Boisen Andersen (la@timekit.io or create an Issue) for questions. PR's are more than welcome!
Features:
The following libraries are bundled together with the SDK:
The library is hosted on NPM, so you can simply go:
npm install timekit-sdk --save
The SDK is UMD (Universal Module Definition) compatible, which means that it can be loaded in various module formats across both browsers and server.
Note: Use plain or minified builds in /dist
when using in browser. In node, /src/timekit.js
will be used through npm (or reference it manually in your require)
ES6 module
import timekit from 'timekit-sdk'
console.log(timekit);
AMD (with e.g. require.js)
require(['timekit-sdk'], function(timekit) {
console.log(timekit);
});
CommonJS2 (in e.g. node.js)
var timekit = require('timekit-sdk');
console.log(timekit);
As a global variable (in browsers)
<script src="timekit-sdk.js"></script>
<script>
console.log(timekit);
</script>
See /examples
for implementation examples.
Only for server-side integrations!
With app keys, your capabilities are scoped on an app-level which mean that you can access data (e.g. bookings) across all resources. It's essential that you only use this for server-side integrations as the key grants full access to your whole timekit app data.
timekit.configure({
appKey: 'live_api_key_4cY2KWMggw95mAdx51eYUO2CyIWI2xup'
})
Your app key can be found in the Timekit admin panel (https://admin.timekit.io)
For client-side integrations!
Resource keys are scoped by the resource and the data that they have access to. The primary use-case is together with our booking.js widget that only acts as a single resource at a time.
Resource keys needs to be accompanied by the resource's email and the app attribute. Note that two types of keys exist: server-token
and client-token
, where only the latter should be used. Please refer to the API reference.
timekit.configure({
app: 'back-to-the-future',
resourceEmail: 'marty.mcfly@timekit.io',
resourceKey: '4cY2KWMggw95mAdx51eYUO2CyIWI2xup'
})
🚨 Important! Resource keys are being phased out as a supported authentication mechanism. We encourage you to use app keys for new Timekit integrations.
The only required configuration is that you set the "app" key to your registered app slug on Timekit.
Here's all the available options:
// Overwrites default config with supplied object, possible keys with default values below
timekit.configure({
apiBaseUrl: 'https://api.timekit.io/', // API endpoint (do not change)
apiVersion: 'v2', // version of API to call (do not change)
inputTimestampFormat: 'Y-m-d h:ia', // default timestamp format that you supply
outputTimestampFormat: 'Y-m-d h:ia', // default timestamp format that you want the API to return
timezone: 'Europe/Copenhagen', // override user's timezone for custom formatted timestamps in another timezone
convertResponseToCamelcase: false, // should keys in JSON response automatically be converted from snake_case to camelCase?
convertRequestToSnakecase: true, // should keys in JSON requests automatically be converted from camelCase to snake_case?
autoFlattenResponse: true // if you keep this set to true, then responses with a "data" key will automatically be flattened to response.data (otherwise you need to access response.data.data). Pagination meta data can be found on response.metaData)
});
// Returns current config object
timekit.getConfig();
All the Timekit API endpoints are supported as methods. For endpoints taking parameters/data, the method argument should be an object with keys named as referenced in the docs - see: https://developers.timekit.io/reference/
If you supply keys as camelCased, they will automatically be converted to snake_case for you. Responses can also be converted to camelCase automatically if you set the config variable convertResponseToCamelcase
to true.
Endpoints/methods:
// App endpoints
timekit.getApp()
// Resource endpoints
timekit.getResources()
timekit.getResource({ id })
timekit.createResource({ ... })
timekit.updateResource({ id, ... })
timekit.resetResourcePassword({ ... })
timekit.getResourceTimezone({ email })
// FindTime endpoints
timekit.findTime({ ... })
timekit.findTimeBulk({ ... })
timekit.findTimeTeam({ ... })
// Availability endpoints
timekit.fetchAvailability({ ... })
timekit.fetchUnAvailableSlots({ ... })
timekit.fetchAvailabilityDates({ ... })
timekit.fetchAvailabilityCounts({ ... })
// Booking endpoints
timekit.getBookings()
timekit.getBooking({ id })
timekit.createBooking({ ... })
timekit.createBookingsBulk({ ... })
timekit.updateBooking({ id, action, ... })
timekit.updateBookingsBulk({ ... })
timekit.deleteBooking({ id })
timekit.getGroupBookings()
timekit.getGroupBooking({ id })
timekit.rescheduleBooking({ id, ... })
// Account endpoints
timekit.getAccounts()
timekit.accountGoogleSignup({ callback }, shouldAutoRedirect)
timekit.accountGoogleSync()
timekit.accountMicrosoftSignup({ callback }, shouldAutoRedirect)
timekit.accountMicrosoftSync()
// Calendar endpoints
timekit.getCalendars()
timekit.getCalendar({ id })
timekit.createCalendar({ ... })
timekit.updateCalendar({ id, ... })
timekit.deleteCalendar({ id })
// Project endpoints
timekit.getProjects()
timekit.getProject({ id })
timekit.getHostedProject({ slug })
timekit.getEmbedProject({ id })
timekit.createProject({ ... })
timekit.updateProject({ id, ... })
timekit.deleteProject({ id })
timekit.getProjectResources({ id })
timekit.addProjectResource({ id, ... })
timekit.setProjectResources({ id, resources })
timekit.removeProjectResource({ id, resourceId })
// Event endpoints
timekit.getEvents({ ... })
timekit.getEvent({ id })
timekit.createEvent({ ... })
timekit.updateEvent({ id, ... })
timekit.deleteEvent({ id })
// Service endpoints
timekit.getServices({ ... })
timekit.getService({ id })
timekit.createService({ ... })
timekit.updateService({ id, ... })
timekit.deleteService({ id })
// Location endpoints
timekit.getLocations({ ... })
timekit.getLocation({ id })
timekit.createLocation({ ... })
timekit.updateLocation({ id, ... })
timekit.deleteLocation({ id })
// service location related endpoints
timekit.getServiceProjects(id)
timekit.getLocationProjects(id)
timekit.getLocationServiceProjects(locationUuid, serviceUuid)
// email template related endpoints
timekit.getEmailTemplates()
timekit.getEmailTemplate(slug)
timekit.updateEmailTemplate({ slug, ... })
// booking reservation
timekit.reserveBooking({ ... })
timekit.extendReservedBooking({ ... })
// Auth endpoints (Note: only used to fetch a resource key)
timekit.auth({ ... })
// Credential endpoints (Note: only used to manage resource keys)
timekit.getCredentials()
timekit.createCredential({ ... })
timekit.deleteCredential({ id })
Request example:
// Using promises
timekit.createBooking({
resource_id: 'd187d6e0-d6cb-409a-ae60-45a8fd0ec879',
graph: 'confirm_decline',
start: '1955-11-12T21:30:00-07:00',
end: '1955-11-12T22:15:00-07:00',
what: 'Catch the lightning',
where: 'Courthouse, Hill Valley, CA 95420, USA',
description: 'The lightning strikes at 10:04 PM exactly! I need you to be there Doc!',
customer: {
name: 'Marty McFly',
email: 'marty.mcfly@timekit.io',
phone: '(916) 555-4385',
voip: 'McFly',
timezone: 'America/Los_Angeles'
}
}).then(function(response){
console.log(response);
}).catch(function(response){
console.log(response);
});
// Using async/await
const response = await timekit.createBooking({ ... })
Response example:
{
// data is the response that was provided by the server
data: {},
// status is the HTTP status code from the server response
status: 200,
// statusText is the HTTP status message from the server response
statusText: 'OK',
// headers the headers that the server responded with
headers: {},
// config is the config that was provided to `axios` for the request
config: {}
}
If you, for some reason, would like direct access to axios's request API, you can call the timekit.makeRequest()
method directly. We'll still set the correct config headers, base url and includes, but otherwise it supports all the settings that axios does.
Example:
timekit.makeRequest({
url: '/bookings',
method: 'post',
data: {
key: 'value'
},
timeout: 1000
}).then(function(response){
console.log(response);
}).catch(function(response){
console.log(response);
});
If you want to inject specific params/query string or data into the next API request, you can use the carry
method. It's handy for e.g. filtering result (search
) or adding pagination (limit
).
Example:
timekit
.carry({
params: {
search: 'graph:confirm_decline',
limit: 10
}
})
.getBookings()
.then(function(response) {
// Response is filtered by the search query and limited to only 10 items
});
The Timekit API have support for dynamically including related models (aka. expand objects). We supports this functionality by providing a chainable/fluent method called .include()
that can be called right before a request.
The method takes unlimited string arguments, with each one being a model that you want included in the response. For nested data (e.g. events grouped by calendar), use the dot notation to dig into relations, like calender.events
.
Example:
timekit
.include('calendars.events', 'users')
.getUserInfo()
.then(function(response) {
// Response contains JSON data with nested info on the user's calendars, events and meetings
});
This is super powerful because it means that you can avoid unnecessary extra requests compared to fetching each resource sequentially.
We use webpack for packaging the library as a module. To build the source files in /src
to /dist
, run:
# install dev dependencies
npm install
# build plain
webpack
# build minified
webpack --config webpack.config.min.js
We use jasmine + karma for unit testing, which works together with webpack.
To run the test suite, simply do:
# install dev dependencies
npm install
# install karma as global
npm install -g karma
# start karma and run
karma start
See Issues for feature requests, bugs etc.
FAQs
JavaScript SDK for the Timekit API (timekit.io)
We found that timekit-sdk demonstrated a not healthy version release cadence and project activity because the last version was released a year ago. It has 2 open source maintainers collaborating on the project.
Did you know?
Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.
Research
Security News
Socket’s threat research team has detected six malicious npm packages typosquatting popular libraries to insert SSH backdoors.
Security News
MITRE's 2024 CWE Top 25 highlights critical software vulnerabilities like XSS, SQL Injection, and CSRF, reflecting shifts due to a refined ranking methodology.
Security News
In this segment of the Risky Business podcast, Feross Aboukhadijeh and Patrick Gray discuss the challenges of tracking malware discovered in open source softare.