@everfund/js-sdk
Advanced tools
Comparing version 2.0.1 to 3.0.0
{ | ||
"name": "@everfund/js-sdk", | ||
"version": "2.0.1", | ||
"version": "3.0.0", | ||
"description": "Plug and Play Donation System", | ||
"author": "Christopher Burns <christopher@everfund.co.uk>", | ||
"module": "build/esm/index.js", | ||
"main": "build/cjs/index.js", | ||
"browser": "build/umd/index.production.js", | ||
"types": "build/types/index.d.ts", | ||
"sideEffects": false, | ||
"license": "MIT", | ||
"engines": { | ||
"node": ">=12" | ||
}, | ||
"main": "./dist/js-sdk.js", | ||
"module": "./dist/js-sdk.mjs", | ||
"types": "./dist/js-sdk.d.ts", | ||
"files": [ | ||
"build/**", | ||
"dist/**", | ||
"src" | ||
], | ||
"scripts": { | ||
"watch": "yarn genversion && microbundle watch", | ||
"deploy": "npm run build && npm publish", | ||
"genversion": "genversion --es6 --semi src/version.ts", | ||
"test": "echo \"Error: no test specified\" && exit 1", | ||
"serve": "serve ./dist", | ||
"format": "yarn prettier --write ." | ||
"build": "tsup --config ./tsup.config.json --dts", | ||
"lint": "eslint \"**/*.ts\"", | ||
"test": "vitest" | ||
}, | ||
"publishConfig": { | ||
"access": "public", | ||
"registry": "https://registry.npmjs.org/" | ||
"dependencies": { | ||
"body-scroll-lock": "4.0.0-beta.0", | ||
"goober": "^2.1.13" | ||
}, | ||
"license": "MIT", | ||
"devDependencies": { | ||
@@ -35,8 +30,13 @@ "@types/body-scroll-lock": "^3.1.0", | ||
"genversion": "^3.1.1", | ||
"typescript": "^4.6.4" | ||
"jsdom": "^22.1.0", | ||
"tsconfig": "workspace:*", | ||
"tsup": "^7.2.0", | ||
"typescript": "^5.1.6", | ||
"vite": "^4.4.9" | ||
}, | ||
"dependencies": { | ||
"body-scroll-lock": "^4.0.0-beta.0", | ||
"goober": "^2.1.9" | ||
} | ||
"publishConfig": { | ||
"access": "public", | ||
"registry": "https://registry.npmjs.org/" | ||
}, | ||
"sideEffects": false | ||
} |
294
src/index.ts
@@ -1,293 +0,5 @@ | ||
import { | ||
disableBodyScroll, | ||
enableBodyScroll, | ||
clearAllBodyScrollLocks, | ||
} from 'body-scroll-lock' | ||
import { checkoutModal } from './donationCheckoutModal'; | ||
import { ModalProps } from './types' | ||
import { version } from './version' | ||
export default checkoutModal; | ||
import { css, keyframes } from 'goober' | ||
export interface CustomWindow extends Window { | ||
Everfund: EverfundClient | ||
} | ||
declare let window: CustomWindow | ||
class EverfundClient { | ||
private donationWidgetOpen: boolean = false | ||
private onSuccess: ModalProps['onSuccess'] = () => {} | ||
private onFailure: ModalProps['onFailure'] = () => {} | ||
private onClose: ModalProps['onClose'] = () => {} | ||
version: string | ||
constructor() { | ||
this.version = version | ||
if (typeof window !== 'undefined') { | ||
this.setupButtonListeners() | ||
this.setupIframeListeners() | ||
} | ||
} | ||
public modal({ | ||
code, | ||
domain, | ||
closeOnSuccess, | ||
onSuccess, | ||
onFailure, | ||
onClose, | ||
}: ModalProps) { | ||
console.warn( | ||
'everfund.modal is deprecated in the next update, please use everfund.donationWidget instead' | ||
) | ||
this.donationWidget({ | ||
code, | ||
domain, | ||
closeOnSuccess, | ||
onSuccess, | ||
onFailure, | ||
onClose, | ||
}) | ||
} | ||
public donationWidget({ | ||
code, | ||
domain, | ||
closeOnSuccess, | ||
onSuccess, | ||
onFailure, | ||
onClose, | ||
}: ModalProps) { | ||
if (onSuccess) this.onSuccess = onSuccess | ||
if (onFailure) this.onFailure = onFailure | ||
if (onClose) this.onClose = onClose | ||
const origin = window.location.origin | ||
let makeQS = function (obj: any) { | ||
var str = [] | ||
for (var p in obj) | ||
if (obj[p] && obj.hasOwnProperty(p)) { | ||
str.push(encodeURIComponent(p) + '=' + encodeURIComponent(obj[p])) | ||
} | ||
return str.join('&') | ||
} | ||
try { | ||
const modalFrame = document.createElement('iframe') | ||
modalFrame.src = `${domain || 'https://evr.fund'}/${code}/modal?${makeQS({ | ||
embed_origin: origin, | ||
embeded: true, | ||
close_on_success: closeOnSuccess, | ||
})}` | ||
// @ts-ignore | ||
modalFrame.allowPaymentRequest = true | ||
const cssEmbedIframe = css({ | ||
border: 'none', | ||
width: '100%', | ||
margin: 0, | ||
height: '100%', | ||
}) | ||
modalFrame.id = 'ef-modal' | ||
modalFrame.className = cssEmbedIframe | ||
modalFrame.ariaModal = 'true' | ||
modalFrame.ariaLabel = 'Everfund Donation Modal' | ||
modalFrame.setAttribute('role', 'donation-modal') | ||
modalFrame.addEventListener('load', function () { | ||
const loadingSpinner = | ||
document.querySelector<HTMLDivElement>('.ldsRing') | ||
const modalWrap = document.querySelector<HTMLDivElement>('.embedModal') | ||
loadingSpinner?.remove() | ||
modalWrap!.style.transform = 'opacity(1)' | ||
}) | ||
const modalWrap = document.createElement('div') | ||
const cssEmbedModal = css({ | ||
pointerEvents: 'all', | ||
zIndex: '9999999', | ||
display: 'flex', | ||
width: '100%', | ||
transform: 'opacity(0)', | ||
transition: 'transform 0.3s ease', | ||
overflowY: 'auto', | ||
'-webkit-overflow-scrolling': 'touch', | ||
height: '100%', | ||
}) | ||
modalWrap.className = `embedModal ${cssEmbedModal}` | ||
modalWrap.appendChild(modalFrame) | ||
const embedContainer = document.createElement('div') | ||
disableBodyScroll(embedContainer) | ||
const loadingSpinner = document.createElement('div') | ||
const cssKeyframeLDsring = keyframes({ | ||
'0%': { transform: 'rotate(0deg)' }, | ||
'100%': { transform: 'rotate(360deg)' }, | ||
}) | ||
const cssLdsRing = css({ | ||
display: 'inline-block', | ||
position: 'absolute', | ||
left: 'calc(50% - 32px)', | ||
top: 'calc(50% - 32px)', | ||
width: '64px', | ||
height: '64px', | ||
'& div': { | ||
boxSizing: 'border-box', | ||
display: 'block', | ||
position: 'absolute', | ||
width: '51px', | ||
height: '51px', | ||
margin: '6px', | ||
border: '6px solid white', | ||
borderRadius: '50%', | ||
animation: `${cssKeyframeLDsring} 1.2s cubic-bezier(0.5, 0, 0.5, 1) infinite`, | ||
borderColor: 'white transparent transparent transparent', | ||
}, | ||
'& div:nth-child(1)': { | ||
animationDelay: ' -0.45s', | ||
}, | ||
'& div:nth-child(2)': { | ||
animationDelay: ' -0.3s', | ||
}, | ||
'& div:nth-child(3)': { | ||
animationDelay: ' -0.15s', | ||
}, | ||
}) | ||
loadingSpinner.className = `ldsRing ${cssLdsRing}` | ||
const div = document.createElement('div') | ||
Array(4) | ||
.fill(4) | ||
.forEach(function () { | ||
loadingSpinner.appendChild(div) | ||
}) | ||
const cssEmbedContainer = css({ | ||
position: 'fixed', | ||
top: '0', | ||
left: '0', | ||
right: '0', | ||
bottom: '0', | ||
background: 'rgba(0, 0, 0, 0.7)', | ||
zIndex: '9999998', | ||
display: 'flex', | ||
justifyContent: 'space-around', | ||
alignItems: 'stretch', | ||
backdropFilter: 'blur(8px)', | ||
}) | ||
embedContainer.className = `embedContainer ${cssEmbedContainer}` | ||
embedContainer.appendChild(loadingSpinner) | ||
embedContainer.appendChild(modalWrap) | ||
// disableBodyScroll(embedContainer) | ||
document.body.appendChild(embedContainer) | ||
modalFrame.setAttribute('tabindex', '0') | ||
modalFrame.focus() | ||
} catch (e) { | ||
console.log(e) | ||
window.location.replace( | ||
`https://${domain || 'evr.fund'}/${code}/modal?${makeQS({ | ||
return_url: origin, | ||
})}` | ||
) | ||
} | ||
} | ||
private setupButtonListeners() { | ||
document.addEventListener( | ||
'click', | ||
function (e: MouseEvent) { | ||
const match = (e.target as HTMLElement).closest('[data-ef-modal]') | ||
if (!match || Everfund.donationWidgetOpen) return | ||
e.preventDefault() | ||
e.stopPropagation() | ||
let code = match.getAttribute('data-ef-modal') | ||
if (!code) { | ||
console.error( | ||
'Everfund: data-ef-modal is required! eg <button data-ef-modal="rjww"> modal </button>' | ||
) | ||
return | ||
} | ||
if ( | ||
!!new RegExp( | ||
'^(https?:\\/\\/)?' + // protocol | ||
'((([a-z\\d]([a-z\\d-]*[a-z\\d])*)\\.)+[a-z]{2,}|' + // domain name | ||
'((\\d{1,3}\\.){3}\\d{1,3}))' + // OR ip (v4) address | ||
'(\\:\\d+)?(\\/[-a-z\\d%_.~+]*)*' + // port and path | ||
'(\\?[;&a-z\\d%_.~+=-]*)?' + // query string | ||
'(\\#[-a-z\\d_]*)?$', | ||
'i' | ||
).test(code) | ||
) { | ||
console.warn( | ||
`Everfund: url's are deprecated please use a code instead` | ||
) | ||
code = new URL(code).pathname.replace('/', '') | ||
} | ||
Everfund.donationWidgetOpen = true | ||
Everfund.donationWidget({ | ||
code, | ||
onSuccess: () => {}, | ||
onFailure: () => {}, | ||
onClose: () => { | ||
clearAllBodyScrollLocks() | ||
}, | ||
}) | ||
}, | ||
false | ||
) | ||
} | ||
private setupIframeListeners() { | ||
window.addEventListener( | ||
'message', | ||
function (e) { | ||
const embed = document.querySelector('.' + 'embedContainer') | ||
switch (e.data.message) { | ||
case 'everfund:ready': | ||
const loadingSpinner = | ||
document.querySelector<HTMLDivElement>('#ldsRing') | ||
const modalWrap = document.querySelector<HTMLDivElement>( | ||
'.' + 'embedModal' | ||
) | ||
loadingSpinner?.remove() | ||
modalWrap!.style.transform = 'opacity(1)' | ||
break | ||
case 'everfund:success': | ||
const data = e.data.content | ||
Everfund.onSuccess(data) | ||
break | ||
case 'everfund:failure': | ||
Everfund.onFailure(e.data.content) | ||
break | ||
case 'everfund:close': | ||
embed && enableBodyScroll(embed) | ||
embed && embed.remove() | ||
Everfund.donationWidgetOpen = false | ||
Everfund.onClose() | ||
clearAllBodyScrollLocks() | ||
break | ||
} | ||
}, | ||
false | ||
) | ||
} | ||
} | ||
const Everfund = new EverfundClient() | ||
export default Everfund | ||
export { checkoutModal }; |
export type SuccessResponse = { | ||
/** Donation Id ie d_XXXXXXX */ | ||
id: string | ||
id: string; | ||
/** Supporter details */ | ||
support?: { | ||
firstName?: string | ||
lastName?: string | ||
phoneNumber?: string | ||
email?: string | ||
firstName?: string; | ||
lastName?: string; | ||
phoneNumber?: string; | ||
email?: string; | ||
address?: { | ||
line1: string | ||
line2?: string | ||
postcode: string | ||
city: string | ||
country: string | ||
} | ||
} | ||
line1: string; | ||
line2?: string; | ||
postcode: string; | ||
city: string; | ||
country: string; | ||
}; | ||
}; | ||
/** Donation Type */ | ||
type?: 'SINGLE' | 'MONTHLY' | ||
type?: 'SINGLE' | 'MONTHLY'; | ||
/** Aggreed to gift aid */ | ||
agreededToGiftAid: boolean | ||
contactByPhone: boolean | ||
contactByPost: boolean | ||
contactByEmail: boolean | ||
agreededToGiftAid: boolean; | ||
contactByPhone: boolean; | ||
contactByPost: boolean; | ||
contactByEmail: boolean; | ||
donation?: { | ||
donationAmount?: number | ||
coveredProcessingFee?: boolean | ||
isDomesticCard?: boolean | ||
isSameCurrency?: boolean | ||
} | ||
} | ||
donationAmount?: number; | ||
coveredProcessingFee?: boolean; | ||
isDomesticCard?: boolean; | ||
isSameCurrency?: boolean; | ||
}; | ||
}; | ||
export type ModalProps = { | ||
/** @deprecated use code field instead */ | ||
donationLink?: string | ||
/** Donation Widget Code get from the dashboard */ | ||
code: string | ||
domain?: string | ||
code: string; | ||
domain?: string; | ||
/** Will close donation modal once payment has succeeded */ | ||
closeOnSuccess?: boolean | null | ||
onSuccess(data: SuccessResponse): void | ||
onFailure(data: Record<string, any>): void | ||
onClose(): void | ||
} | ||
closeOnSuccess?: boolean | null; | ||
onSuccess?(data: SuccessResponse): void; | ||
onFailure?(data: Record<string, unknown>): void; | ||
onClose?(): void; | ||
}; |
// Generated by genversion. | ||
export const version = '2.0.1' | ||
export const version = '3.0.0'; |
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
Minified code
QualityThis package contains minified code. This may be harmless in some cases where minified code is included in packaged libraries, however packages on npm should not minify code.
Found 1 instance in 1 package
No README
QualityPackage does not have a README. This may indicate a failed publish or a low quality package.
Found 1 instance in 1 package
No tests
QualityPackage does not have any tests. This is a strong signal of a poorly maintained or low quality package.
Found 1 instance in 1 package
1
166
104266
8
17
597
1
Updatedgoober@^2.1.13