@casl/react 4.0.0 → 5.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,2 +1,2 @@
1
- import t,{PureComponent as r,createElement as n}from"react";function i(t,r){if("object"!=typeof t||!t)return t;var n=t[Symbol.toPrimitive];if(void 0!==n){var i=n.call(t,r||"default");if("object"!=typeof i)return i;throw new TypeError("@@toPrimitive must return a primitive value.")}return("string"===r?String:Number)(t)}function u(t){var r=i(t,"string");return"symbol"==typeof r?r:String(r)}function e(t,r){for(var n=0;n<r.length;n++){var i=r[n];i.enumerable=i.enumerable||false;i.configurable=true;if("value"in i)i.writable=true;Object.defineProperty(t,u(i.key),i)}}function o(t,r,n){if(r)e(t.prototype,r);if(n)e(t,n);Object.defineProperty(t,"prototype",{writable:false});return t}function f(){f=Object.assign?Object.assign.bind():function(t){for(var r=1;r<arguments.length;r++){var n=arguments[r];for(var i in n)if(Object.prototype.hasOwnProperty.call(n,i))t[i]=n[i]}return t};return f.apply(this,arguments)}function c(t,r){t.prototype=Object.create(r.prototype);t.prototype.constructor=t;a(t,r)}function a(t,r){a=Object.setPrototypeOf?Object.setPrototypeOf.bind():function t(r,n){r.__proto__=n;return r};return a(t,r)}var s=function t(){};var v=function(t){c(r,t);function r(){var r;for(var n=arguments.length,i=new Array(n),u=0;u<n;u++)i[u]=arguments[u];r=t.call.apply(t,[this].concat(i))||this;r.t=false;r.i=null;r.u=s;return r}var n=r.prototype;n.componentWillUnmount=function t(){this.u()};n.o=function _connectToAbility(t){var r=this;if(t===this.i)return;this.u();this.i=null;if(t){this.i=t;this.u=t.on("updated",(function(){return r.forceUpdate()}))}};n.v=function t(){var r=this.props;var n=r.of||r.a||r.an||r.this||r.on;var i=r.not?"cannot":"can";return r.ability[i](r.I||r.do,n,r.field)};n.render=function t(){this.o(this.props.ability);this.t=this.v();return this.props.passThrough||this.t?this.h():null};n.h=function t(){var r=this.props,n=r.children,i=r.ability;var u=typeof n==="function"?n(this.t,i):n;return u};o(r,[{key:"allowed",get:function t(){return this.t}}]);return r}(r);function h(t){var r;return r=function(t){c(r,t);function r(){return t.apply(this,arguments)||this}return r}(v),r.defaultProps={ability:t},r}function l(t){return function(r){return n(t,{children:function t(i){return n(v,f({ability:i},r))}})}}function useAbility(r){if(process.env.NODE_ENV!=="production"&&typeof t.useContext!=="function")throw new Error("You must use React >= 16.8 in order to use useAbility()");var n=t.useContext(r);var i=t.useState(),u=i[0],e=i[1];t.useEffect((function(){return n.on("updated",(function(t){if(t.rules!==u)e(t.rules)}))}),[]);return n}export{v as Can,h as createCanBoundTo,l as createContextualCan,useAbility};
1
+ import t,{PureComponent as n,createElement as r}from"react";function i(t,n){for(var r=0;r<n.length;r++){var i=n[r];i.enumerable=i.enumerable||!1,i.configurable=!0,"value"in i&&(i.writable=!0),Object.defineProperty(t,a(i.key),i)}}function u(t,n,r){return n&&i(t.prototype,n),Object.defineProperty(t,"prototype",{writable:!1}),t}function e(){return e=Object.assign?Object.assign.bind():function(t){for(var n=1;n<arguments.length;n++){var r=arguments[n];for(var i in r)({}).hasOwnProperty.call(r,i)&&(t[i]=r[i])}return t},e.apply(null,arguments)}function o(t,n){t.prototype=Object.create(n.prototype),t.prototype.constructor=t,f(t,n)}function f(t,n){return f=Object.setPrototypeOf?Object.setPrototypeOf.bind():function(t,n){return t.__proto__=n,t},f(t,n)}function c(t,n){if("object"!=typeof t||!t)return t;var r=t[Symbol.toPrimitive];if(void 0!==r){var i=r.call(t,n);if("object"!=typeof i)return i;throw new TypeError("@@toPrimitive must return a primitive value.")}return String(t)}function a(t){var n=c(t,"string");return"symbol"==typeof n?n:n+""}var s=function t(){};var v=function(t){function n(){var n;for(var r=arguments.length,i=new Array(r),u=0;u<r;u++)i[u]=arguments[u];n=t.call.apply(t,[this].concat(i))||this;n.i=false;n.u=null;n.o=s;n.state={t:true};return n}o(n,t);var r=n.prototype;r.componentWillUnmount=function t(){this.o()};r.v=function _connectToAbility(t){var n=this;if(t===this.u)return;this.o();this.u=null;if(t){this.u=t;this.o=t.on("updated",(function(){return n.setState({t:!n.state.t})}))}};r.h=function t(){var n=this.props;var r=n.of||n.a||n.an||n.this||n.on;var i=n.not?"cannot":"can";return n.ability[i](n.I||n.do,r,n.field)};r.render=function t(){this.v(this.props.ability);this.i=this.h();return this.props.passThrough||this.i?this.l():null};r.l=function t(){var n=this.props,r=n.children,i=n.ability;var u=typeof r==="function"?r(this.i,i):r;return u};return u(n,[{key:"allowed",get:function t(){return this.i}}])}(n);function h(t){return function(n){return r(t,{children:function t(i){return r(v,e({},n,{ability:n.ability||i}))}})}}function useAbility(n){var r=t.useContext(n);var i=t.useState(),u=i[0],e=i[1];t.useEffect((function(){return r.on("updated",(function(t){if(t.rules!==u)e(t.rules)}))}),[]);return r}export{v as Can,h as createContextualCan,useAbility};
2
2
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":["../../src/Can.ts","../../src/factory.ts","../../src/hooks/useAbility.ts"],"sourcesContent":["import { PureComponent, ReactNode } from 'react';\nimport {\n Unsubscribe,\n AbilityTuple,\n SubjectType,\n AnyAbility,\n Generics,\n Abilities,\n IfString,\n} from '@casl/ability';\n\nconst noop = () => {};\n\ntype AbilityCanProps<\n T extends Abilities,\n Else = IfString<T, { do: T } | { I: T }>\n> = T extends AbilityTuple\n ? { do: T[0], on: T[1], field?: string } |\n { I: T[0], a: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], an: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], this: Exclude<T[1], SubjectType>, field?: string }\n : Else;\n\ninterface ExtraProps {\n not?: boolean\n passThrough?: boolean\n}\n\ninterface CanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\ninterface BoundCanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability?: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\nexport type CanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & CanExtraProps<T>;\nexport type BoundCanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & BoundCanExtraProps<T>;\n\nexport class Can<\n T extends AnyAbility,\n IsBound extends boolean = false\n> extends PureComponent<IsBound extends true ? BoundCanProps<T> : CanProps<T>> {\n private _isAllowed: boolean = false;\n private _ability: T | null = null;\n private _unsubscribeFromAbility: Unsubscribe = noop;\n\n componentWillUnmount() {\n this._unsubscribeFromAbility();\n }\n\n private _connectToAbility(ability?: T) {\n if (ability === this._ability) {\n return;\n }\n\n this._unsubscribeFromAbility();\n this._ability = null;\n\n if (ability) {\n this._ability = ability;\n this._unsubscribeFromAbility = ability.on('updated', () => this.forceUpdate());\n }\n }\n\n get allowed() {\n return this._isAllowed;\n }\n\n private _canRender(): boolean {\n const props: any = this.props;\n const subject = props.of || props.a || props.an || props.this || props.on;\n const can = props.not ? 'cannot' : 'can';\n\n return props.ability[can](props.I || props.do, subject, props.field);\n }\n\n render() {\n this._connectToAbility(this.props.ability);\n this._isAllowed = this._canRender();\n return this.props.passThrough || this._isAllowed ? this._renderChildren() : null;\n }\n\n private _renderChildren() {\n const { children, ability } = this.props;\n const elements = typeof children === 'function'\n ? children(this._isAllowed, ability as any)\n : children;\n\n return elements as ReactNode;\n }\n}\n","import { createElement as h, ComponentClass, Consumer, FunctionComponent } from 'react';\nimport { AnyAbility } from '@casl/ability';\nimport { Can, BoundCanProps } from './Can';\n\ninterface BoundCanClass<T extends AnyAbility> extends ComponentClass<BoundCanProps<T>> {\n new (props: BoundCanProps<T>, context?: any): Can<T, true>\n}\n\nexport function createCanBoundTo<T extends AnyAbility>(ability: T): BoundCanClass<T> {\n return class extends Can<T, true> {\n static defaultProps = { ability } as BoundCanClass<T>['defaultProps'];\n };\n}\n\nexport function createContextualCan<T extends AnyAbility>(\n Getter: Consumer<T>\n): FunctionComponent<BoundCanProps<T>> {\n return (props: BoundCanProps<T>) => h(Getter, {\n children: (ability: T) => h(Can, {\n ability,\n ...props,\n } as any)\n });\n}\n","import React from 'react';\nimport { AnyAbility } from '@casl/ability';\n\nexport function useAbility<T extends AnyAbility>(context: React.Context<T>): T {\n if (process.env.NODE_ENV !== 'production' && typeof React.useContext !== 'function') {\n /* istanbul ignore next */\n throw new Error('You must use React >= 16.8 in order to use useAbility()');\n }\n\n const ability = React.useContext<T>(context);\n const [rules, setRules] = React.useState<T['rules']>();\n\n React.useEffect(() => ability.on('updated', (event) => {\n if (event.rules !== rules) {\n setRules(event.rules);\n }\n }), []);\n\n return ability;\n}\n"],"names":["noop","Can","_PureComponent","_inheritsLoose","_this","_len","arguments","length","args","Array","_key","call","apply","this","concat","_isAllowed","_ability","_unsubscribeFromAbility","_proto","prototype","componentWillUnmount","_connectToAbility","ability","_this2","on","forceUpdate","_canRender","props","subject","of","a","an","can","not","I","do","field","render","passThrough","_renderChildren","_this$props","children","elements","_createClass","key","get","PureComponent","createCanBoundTo","_Class","_Can","defaultProps","createContextualCan","Getter","h","_extends","useAbility","context","process","env","NODE_ENV","React","useContext","Error","_React$useState","useState","rules","setRules","useEffect","event"],"mappings":"imCAWA,IAAMA,EAAO,SAAPA,MAgCOC,IAAAA,WAAGC,GAAAC,EAAAF,EAAAC,GAAA,SAAAD,IAAA,IAAAG,EAAA,IAAA,IAAAC,EAAAC,UAAAC,OAAAC,EAAAC,IAAAA,MAAAJ,GAAAK,EAAA,EAAAA,EAAAL,EAAAK,IAAAF,EAAAE,GAAAJ,UAAAI,GAAAN,EAAAF,EAAAS,KAAAC,MAAAV,EAAA,CAAAW,MAAAC,OAAAN,KAAAK,KAAAT,EAINW,EAAsB,MAAKX,EAC3BY,EAAqB,KAAIZ,EACzBa,EAAuCjB,EAAI,OAAAI,CAAA,CAAA,IAAAc,EAAAjB,EAAAkB,UAAAD,EAEnDE,qBAAA,SAAAA,IACEP,KAAKI,KACNC,EAEOG,EAAR,SAAAA,kBAA0BC,GAAa,IAAAC,EAAAV,KACrC,GAAIS,IAAYT,KAAKG,EACnB,OAGFH,KAAKI,IACLJ,KAAKG,EAAW,KAEhB,GAAIM,EAAS,CACXT,KAAKG,EAAWM,EAChBT,KAAKI,EAA0BK,EAAQE,GAAG,WAAW,WAAA,OAAMD,EAAKE,gBAClE,GACDP,EAMOQ,EAAR,SAAAA,IACE,IAAMC,EAAad,KAAKc,MACxB,IAAMC,EAAUD,EAAME,IAAMF,EAAMG,GAAKH,EAAMI,IAAMJ,EAAMd,MAAQc,EAAMH,GACvE,IAAMQ,EAAML,EAAMM,IAAM,SAAW,MAEnC,OAAON,EAAML,QAAQU,GAAKL,EAAMO,GAAKP,EAAMQ,GAAIP,EAASD,EAAMS,QAC/DlB,EAEDmB,OAAA,SAAAA,IACExB,KAAKQ,EAAkBR,KAAKc,MAAML,SAClCT,KAAKE,EAAaF,KAAKa,IACvB,OAAOb,KAAKc,MAAMW,aAAezB,KAAKE,EAAaF,KAAK0B,IAAoB,MAC7ErB,EAEOqB,EAAR,SAAAA,IACE,IAAAC,EAA8B3B,KAAKc,MAA3Bc,EAAQD,EAARC,SAAUnB,EAAOkB,EAAPlB,QAClB,IAAMoB,SAAkBD,IAAa,WACjCA,EAAS5B,KAAKE,EAAYO,GAC1BmB,EAEJ,OAAOC,GACRC,EAAA1C,EAAA,CAAA,CAAA2C,IAAA,UAAAC,IAzBD,SAAAA,IACE,OAAOhC,KAAKE,CACd,KAAC,OAAAd,CAAA,EAzBO6C,GCtCH,SAASC,EAAuCzB,GAA8B,IAAA0B,EACnF,OAAAA,WAAAC,GAAA9C,EAAA6C,EAAAC,GAAA,SAAAD,IAAA,OAAAC,EAAArC,MAAAC,KAAAP,YAAAO,IAAA,CAAA,OAAAmC,CAAA,EAAqB/C,GAAG+C,EACfE,aAAe,CAAE5B,QAAAA,GAAS0B,CAErC,CAEO,SAASG,EACdC,GAEA,OAAO,SAACzB,GAAuB,OAAK0B,EAAED,EAAQ,CAC5CX,SAAU,SAAAA,EAACnB,GAAU,OAAK+B,EAAEpD,EAAGqD,EAAA,CAC7BhC,QAAAA,GACGK,GACI,GACT,CACJ,CCpBO,SAAS4B,WAAiCC,GAC/C,GAAIC,QAAQC,IAAIC,WAAa,qBAAuBC,EAAMC,aAAe,WAEvE,MAAM,IAAIC,MAAM,2DAGlB,IAAMxC,EAAUsC,EAAMC,WAAcL,GACpC,IAAAO,EAA0BH,EAAMI,WAAzBC,EAAKF,EAAA,GAAEG,EAAQH,EAAA,GAEtBH,EAAMO,WAAU,WAAA,OAAM7C,EAAQE,GAAG,WAAW,SAAC4C,GAC3C,GAAIA,EAAMH,QAAUA,EAClBC,EAASE,EAAMH,MAEnB,GAAE,GAAE,IAEJ,OAAO3C,CACT"}
1
+ {"version":3,"file":"index.js","sources":["../../src/Can.ts","../../src/factory.ts","../../src/hooks/useAbility.ts"],"sourcesContent":["import { PureComponent, ReactNode } from 'react';\nimport {\n Unsubscribe,\n AbilityTuple,\n SubjectType,\n AnyAbility,\n Generics,\n Abilities,\n IfString,\n} from '@casl/ability';\n\nconst noop = () => {};\n\ntype AbilityCanProps<\n T extends Abilities,\n Else = IfString<T, { do: T } | { I: T }>\n> = T extends AbilityTuple\n ? { do: T[0], on: T[1], field?: string } |\n { I: T[0], a: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], an: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], this: Exclude<T[1], SubjectType>, field?: string }\n : Else;\n\ninterface ExtraProps {\n not?: boolean\n passThrough?: boolean\n}\n\ninterface CanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\ninterface BoundCanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability?: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\nexport type CanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & CanExtraProps<T>;\nexport type BoundCanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & BoundCanExtraProps<T>;\n\nexport class Can<T extends AnyAbility> extends PureComponent<CanProps<T>, { t: boolean }> {\n private _isAllowed = false;\n private _ability: T | null = null;\n private _unsubscribeFromAbility: Unsubscribe = noop;\n state = { t: true }\n\n componentWillUnmount() {\n this._unsubscribeFromAbility();\n }\n\n private _connectToAbility(ability?: T) {\n if (ability === this._ability) {\n return;\n }\n\n this._unsubscribeFromAbility();\n this._ability = null;\n\n if (ability) {\n this._ability = ability;\n this._unsubscribeFromAbility = ability.on('updated', () => this.setState({ t: !this.state.t }));\n }\n }\n\n get allowed() {\n return this._isAllowed;\n }\n\n private _canRender(): boolean {\n const props: any = this.props;\n const subject = props.of || props.a || props.an || props.this || props.on;\n const can = props.not ? 'cannot' : 'can';\n\n return props.ability[can](props.I || props.do, subject, props.field);\n }\n\n render() {\n this._connectToAbility(this.props.ability);\n this._isAllowed = this._canRender();\n return this.props.passThrough || this._isAllowed ? this._renderChildren() : null;\n }\n\n private _renderChildren() {\n const { children, ability } = this.props;\n const elements = typeof children === 'function'\n ? children(this._isAllowed, ability as any)\n : children;\n\n return elements as ReactNode;\n }\n}\n","import { AnyAbility } from '@casl/ability';\nimport { Consumer, FunctionComponent, createElement } from 'react';\nimport { BoundCanProps, Can } from './Can';\n\nexport function createContextualCan<T extends AnyAbility>(\n Getter: Consumer<T>\n): FunctionComponent<BoundCanProps<T>> {\n return (props: BoundCanProps<T>) => createElement(Getter, {\n children: (ability: T) => \n createElement(Can, { ...props, ability: props.ability || ability } as any),\n });\n}\n","import React from 'react';\nimport { AnyAbility } from '@casl/ability';\n\nexport function useAbility<T extends AnyAbility>(context: React.Context<T>): T {\n const ability = React.useContext<T>(context);\n const [rules, setRules] = React.useState<T['rules']>();\n\n React.useEffect(() => ability.on('updated', (event) => {\n if (event.rules !== rules) {\n setRules(event.rules);\n }\n }), []);\n\n return ability;\n}\n"],"names":["noop","Can","_PureComponent","_this","_len","arguments","length","args","Array","_key","call","apply","this","concat","_isAllowed","_ability","_unsubscribeFromAbility","state","t","_inheritsLoose","_proto","prototype","componentWillUnmount","_connectToAbility","ability","_this2","on","setState","_canRender","props","subject","of","a","an","can","not","I","do","field","render","passThrough","_renderChildren","_this$props","children","elements","_createClass","key","get","PureComponent","createContextualCan","Getter","createElement","_extends","useAbility","context","React","useContext","_React$useState","useState","rules","setRules","useEffect","event"],"mappings":"shCAWA,IAAMA,EAAO,SAAPA,MAgCOC,IAAAA,WAAGC,GAAA,SAAAD,IAAA,IAAAE,EAAA,IAAA,IAAAC,EAAAC,UAAAC,OAAAC,EAAAC,IAAAA,MAAAJ,GAAAK,EAAA,EAAAA,EAAAL,EAAAK,IAAAF,EAAAE,GAAAJ,UAAAI,GAAAN,EAAAD,EAAAQ,KAAAC,MAAAT,EAAA,CAAAU,MAAAC,OAAAN,KAAAK,KAAAT,EACNW,EAAa,MAAKX,EAClBY,EAAqB,KAAIZ,EACzBa,EAAuChB,EAAIG,EACnDc,MAAQ,CAAEC,EAAG,MAAM,OAAAf,CAAA,CAAAgB,EAAAlB,EAAAC,GAAA,IAAAkB,EAAAnB,EAAAoB,UAAAD,EAEnBE,qBAAA,SAAAA,IACEV,KAAKI,KACNI,EAEOG,EAAR,SAAQA,kBAAkBC,GAAa,IAAAC,EAAAb,KACrC,GAAIY,IAAYZ,KAAKG,EACnB,OAGFH,KAAKI,IACLJ,KAAKG,EAAW,KAEhB,GAAIS,EAAS,CACXZ,KAAKG,EAAWS,EAChBZ,KAAKI,EAA0BQ,EAAQE,GAAG,WAAW,WAAA,OAAMD,EAAKE,SAAS,CAAET,GAAIO,EAAKR,MAAMC,MAC5F,GACDE,EAMOQ,EAAR,SAAQA,IACN,IAAMC,EAAajB,KAAKiB,MACxB,IAAMC,EAAUD,EAAME,IAAMF,EAAMG,GAAKH,EAAMI,IAAMJ,EAAMjB,MAAQiB,EAAMH,GACvE,IAAMQ,EAAML,EAAMM,IAAM,SAAW,MAEnC,OAAON,EAAML,QAAQU,GAAKL,EAAMO,GAAKP,EAAMQ,GAAIP,EAASD,EAAMS,QAC/DlB,EAEDmB,OAAA,SAAAA,IACE3B,KAAKW,EAAkBX,KAAKiB,MAAML,SAClCZ,KAAKE,EAAaF,KAAKgB,IACvB,OAAOhB,KAAKiB,MAAMW,aAAe5B,KAAKE,EAAaF,KAAK6B,IAAoB,MAC7ErB,EAEOqB,EAAR,SAAQA,IACN,IAAAC,EAA8B9B,KAAKiB,MAA3Bc,EAAQD,EAARC,SAAUnB,EAAOkB,EAAPlB,QAClB,IAAMoB,SAAkBD,IAAa,WACjCA,EAAS/B,KAAKE,EAAYU,GAC1BmB,EAEJ,OAAOC,GACR,OAAAC,EAAA5C,EAAA,CAAA,CAAA6C,IAAA,UAAAC,IAzBD,SAAAA,IACE,OAAOnC,KAAKE,CACd,IAAC,EA1B4CkC,GCvCxC,SAASC,EACdC,GAEA,OAAO,SAACrB,GAAuB,OAAKsB,EAAcD,EAAQ,CACxDP,SAAU,SAAVA,EAAWnB,GAAU,OACnB2B,EAAclD,EAAGmD,KAAOvB,EAAK,CAAEL,QAASK,EAAML,SAAWA,IAAiB,GAC5E,CACJ,CCRO,SAAS6B,WAAiCC,GAC/C,IAAM9B,EAAU+B,EAAMC,WAAcF,GACpC,IAAAG,EAA0BF,EAAMG,WAAzBC,EAAKF,EAAA,GAAEG,EAAQH,EAAA,GAEtBF,EAAMM,WAAU,WAAA,OAAMrC,EAAQE,GAAG,WAAW,SAACoC,GAC3C,GAAIA,EAAMH,QAAUA,EAClBC,EAASE,EAAMH,MAEnB,GAAE,GAAE,IAEJ,OAAOnC,CACT"}
@@ -1,2 +1,2 @@
1
- import t,{PureComponent as i,createElement as n}from"react";const s=()=>{};class e extends i{constructor(...t){super(...t);this.t=false;this.i=null;this.o=s}componentWillUnmount(){this.o()}u(t){if(t===this.i)return;this.o();this.i=null;if(t){this.i=t;this.o=t.on("updated",(()=>this.forceUpdate()))}}get allowed(){return this.t}h(){const t=this.props;const i=t.of||t.a||t.an||t.this||t.on;const n=t.not?"cannot":"can";return t.ability[n](t.I||t.do,i,t.field)}render(){this.u(this.props.ability);this.t=this.h();return this.props.passThrough||this.t?this.l():null}l(){const{children:t,ability:i}=this.props;const n=typeof t==="function"?t(this.t,i):t;return n}}function r(t){var i;return i=class extends e{},i.defaultProps={ability:t},i}function o(t){return i=>n(t,{children:t=>n(e,Object.assign({ability:t},i))})}function useAbility(i){if(process.env.NODE_ENV!=="production"&&typeof t.useContext!=="function")throw new Error("You must use React >= 16.8 in order to use useAbility()");const n=t.useContext(i);const[s,e]=t.useState();t.useEffect((()=>n.on("updated",(t=>{if(t.rules!==s)e(t.rules)}))),[]);return n}export{e as Can,r as createCanBoundTo,o as createContextualCan,useAbility};
1
+ import t,{PureComponent as i,createElement as n}from"react";const s=()=>{};class e extends i{constructor(...t){super(...t);this.i=false;this.h=null;this.o=s;this.state={t:true}}componentWillUnmount(){this.o()}u(t){if(t===this.h)return;this.o();this.h=null;if(t){this.h=t;this.o=t.on("updated",(()=>this.setState({t:!this.state.t})))}}get allowed(){return this.i}l(){const t=this.props;const i=t.of||t.a||t.an||t.this||t.on;const n=t.not?"cannot":"can";return t.ability[n](t.I||t.do,i,t.field)}render(){this.u(this.props.ability);this.i=this.l();return this.props.passThrough||this.i?this.p():null}p(){const{children:t,ability:i}=this.props;const n=typeof t==="function"?t(this.i,i):t;return n}}function r(t){return i=>n(t,{children:t=>n(e,Object.assign({},i,{ability:i.ability||t}))})}function useAbility(i){const n=t.useContext(i);const[s,e]=t.useState();t.useEffect((()=>n.on("updated",(t=>{if(t.rules!==s)e(t.rules)}))),[]);return n}export{e as Can,r as createContextualCan,useAbility};
2
2
  //# sourceMappingURL=index.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.mjs","sources":["../../src/Can.ts","../../src/factory.ts","../../src/hooks/useAbility.ts"],"sourcesContent":["import { PureComponent, ReactNode } from 'react';\nimport {\n Unsubscribe,\n AbilityTuple,\n SubjectType,\n AnyAbility,\n Generics,\n Abilities,\n IfString,\n} from '@casl/ability';\n\nconst noop = () => {};\n\ntype AbilityCanProps<\n T extends Abilities,\n Else = IfString<T, { do: T } | { I: T }>\n> = T extends AbilityTuple\n ? { do: T[0], on: T[1], field?: string } |\n { I: T[0], a: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], an: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], this: Exclude<T[1], SubjectType>, field?: string }\n : Else;\n\ninterface ExtraProps {\n not?: boolean\n passThrough?: boolean\n}\n\ninterface CanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\ninterface BoundCanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability?: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\nexport type CanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & CanExtraProps<T>;\nexport type BoundCanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & BoundCanExtraProps<T>;\n\nexport class Can<\n T extends AnyAbility,\n IsBound extends boolean = false\n> extends PureComponent<IsBound extends true ? BoundCanProps<T> : CanProps<T>> {\n private _isAllowed: boolean = false;\n private _ability: T | null = null;\n private _unsubscribeFromAbility: Unsubscribe = noop;\n\n componentWillUnmount() {\n this._unsubscribeFromAbility();\n }\n\n private _connectToAbility(ability?: T) {\n if (ability === this._ability) {\n return;\n }\n\n this._unsubscribeFromAbility();\n this._ability = null;\n\n if (ability) {\n this._ability = ability;\n this._unsubscribeFromAbility = ability.on('updated', () => this.forceUpdate());\n }\n }\n\n get allowed() {\n return this._isAllowed;\n }\n\n private _canRender(): boolean {\n const props: any = this.props;\n const subject = props.of || props.a || props.an || props.this || props.on;\n const can = props.not ? 'cannot' : 'can';\n\n return props.ability[can](props.I || props.do, subject, props.field);\n }\n\n render() {\n this._connectToAbility(this.props.ability);\n this._isAllowed = this._canRender();\n return this.props.passThrough || this._isAllowed ? this._renderChildren() : null;\n }\n\n private _renderChildren() {\n const { children, ability } = this.props;\n const elements = typeof children === 'function'\n ? children(this._isAllowed, ability as any)\n : children;\n\n return elements as ReactNode;\n }\n}\n","import { createElement as h, ComponentClass, Consumer, FunctionComponent } from 'react';\nimport { AnyAbility } from '@casl/ability';\nimport { Can, BoundCanProps } from './Can';\n\ninterface BoundCanClass<T extends AnyAbility> extends ComponentClass<BoundCanProps<T>> {\n new (props: BoundCanProps<T>, context?: any): Can<T, true>\n}\n\nexport function createCanBoundTo<T extends AnyAbility>(ability: T): BoundCanClass<T> {\n return class extends Can<T, true> {\n static defaultProps = { ability } as BoundCanClass<T>['defaultProps'];\n };\n}\n\nexport function createContextualCan<T extends AnyAbility>(\n Getter: Consumer<T>\n): FunctionComponent<BoundCanProps<T>> {\n return (props: BoundCanProps<T>) => h(Getter, {\n children: (ability: T) => h(Can, {\n ability,\n ...props,\n } as any)\n });\n}\n","import React from 'react';\nimport { AnyAbility } from '@casl/ability';\n\nexport function useAbility<T extends AnyAbility>(context: React.Context<T>): T {\n if (process.env.NODE_ENV !== 'production' && typeof React.useContext !== 'function') {\n /* istanbul ignore next */\n throw new Error('You must use React >= 16.8 in order to use useAbility()');\n }\n\n const ability = React.useContext<T>(context);\n const [rules, setRules] = React.useState<T['rules']>();\n\n React.useEffect(() => ability.on('updated', (event) => {\n if (event.rules !== rules) {\n setRules(event.rules);\n }\n }), []);\n\n return ability;\n}\n"],"names":["noop","Can","PureComponent","constructor","args","super","this","_isAllowed","_ability","_unsubscribeFromAbility","componentWillUnmount","_connectToAbility","ability","on","forceUpdate","allowed","_canRender","props","subject","of","a","an","can","not","I","do","field","render","passThrough","_renderChildren","children","elements","createCanBoundTo","_Class","defaultProps","createContextualCan","Getter","h","Object","assign","useAbility","context","process","env","NODE_ENV","React","useContext","Error","rules","setRules","useState","useEffect","event"],"mappings":"4DAWA,MAAMA,EAAOA,OAgCN,MAAMC,UAGHC,EAAqEC,WAAAA,IAAAC,GAAAC,SAAAD,GAAAE,KACrEC,EAAsB,MAAKD,KAC3BE,EAAqB,KAAIF,KACzBG,EAAuCT,CAAI,CAEnDU,oBAAAA,GACEJ,KAAKG,GACP,CAEQE,CAAAA,CAAkBC,GACxB,GAAIA,IAAYN,KAAKE,EACnB,OAGFF,KAAKG,IACLH,KAAKE,EAAW,KAEhB,GAAII,EAAS,CACXN,KAAKE,EAAWI,EAChBN,KAAKG,EAA0BG,EAAQC,GAAG,WAAW,IAAMP,KAAKQ,eAClE,CACF,CAEA,WAAIC,GACF,OAAOT,KAAKC,CACd,CAEQS,CAAAA,GACN,MAAMC,EAAaX,KAAKW,MACxB,MAAMC,EAAUD,EAAME,IAAMF,EAAMG,GAAKH,EAAMI,IAAMJ,EAAMX,MAAQW,EAAMJ,GACvE,MAAMS,EAAML,EAAMM,IAAM,SAAW,MAEnC,OAAON,EAAML,QAAQU,GAAKL,EAAMO,GAAKP,EAAMQ,GAAIP,EAASD,EAAMS,MAChE,CAEAC,MAAAA,GACErB,KAAKK,EAAkBL,KAAKW,MAAML,SAClCN,KAAKC,EAAaD,KAAKU,IACvB,OAAOV,KAAKW,MAAMW,aAAetB,KAAKC,EAAaD,KAAKuB,IAAoB,IAC9E,CAEQA,CAAAA,GACN,MAAMC,SAAEA,EAAQlB,QAAEA,GAAYN,KAAKW,MACnC,MAAMc,SAAkBD,IAAa,WACjCA,EAASxB,KAAKC,EAAYK,GAC1BkB,EAEJ,OAAOC,CACT,ECtFK,SAASC,EAAuCpB,GAA8B,IAAAqB,EACnF,OAAAA,EAAO,cAAchC,IAEpBgC,EADQC,aAAe,CAAEtB,WAASqB,CAErC,CAEO,SAASE,EACdC,GAEA,OAAQnB,GAA4BoB,EAAED,EAAQ,CAC5CN,SAAWlB,GAAeyB,EAAEpC,EAAGqC,OAAAC,OAAA,CAC7B3B,WACGK,KAGT,CCpBO,SAASuB,WAAiCC,GAC/C,GAAIC,QAAQC,IAAIC,WAAa,qBAAuBC,EAAMC,aAAe,WAEvE,MAAM,IAAIC,MAAM,2DAGlB,MAAMnC,EAAUiC,EAAMC,WAAcL,GACpC,MAAOO,EAAOC,GAAYJ,EAAMK,WAEhCL,EAAMM,WAAU,IAAMvC,EAAQC,GAAG,WAAYuC,IAC3C,GAAIA,EAAMJ,QAAUA,EAClBC,EAASG,EAAMJ,MACjB,KACE,IAEJ,OAAOpC,CACT"}
1
+ {"version":3,"file":"index.mjs","sources":["../../src/Can.ts","../../src/factory.ts","../../src/hooks/useAbility.ts"],"sourcesContent":["import { PureComponent, ReactNode } from 'react';\nimport {\n Unsubscribe,\n AbilityTuple,\n SubjectType,\n AnyAbility,\n Generics,\n Abilities,\n IfString,\n} from '@casl/ability';\n\nconst noop = () => {};\n\ntype AbilityCanProps<\n T extends Abilities,\n Else = IfString<T, { do: T } | { I: T }>\n> = T extends AbilityTuple\n ? { do: T[0], on: T[1], field?: string } |\n { I: T[0], a: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], an: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], this: Exclude<T[1], SubjectType>, field?: string }\n : Else;\n\ninterface ExtraProps {\n not?: boolean\n passThrough?: boolean\n}\n\ninterface CanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\ninterface BoundCanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability?: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\nexport type CanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & CanExtraProps<T>;\nexport type BoundCanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & BoundCanExtraProps<T>;\n\nexport class Can<T extends AnyAbility> extends PureComponent<CanProps<T>, { t: boolean }> {\n private _isAllowed = false;\n private _ability: T | null = null;\n private _unsubscribeFromAbility: Unsubscribe = noop;\n state = { t: true }\n\n componentWillUnmount() {\n this._unsubscribeFromAbility();\n }\n\n private _connectToAbility(ability?: T) {\n if (ability === this._ability) {\n return;\n }\n\n this._unsubscribeFromAbility();\n this._ability = null;\n\n if (ability) {\n this._ability = ability;\n this._unsubscribeFromAbility = ability.on('updated', () => this.setState({ t: !this.state.t }));\n }\n }\n\n get allowed() {\n return this._isAllowed;\n }\n\n private _canRender(): boolean {\n const props: any = this.props;\n const subject = props.of || props.a || props.an || props.this || props.on;\n const can = props.not ? 'cannot' : 'can';\n\n return props.ability[can](props.I || props.do, subject, props.field);\n }\n\n render() {\n this._connectToAbility(this.props.ability);\n this._isAllowed = this._canRender();\n return this.props.passThrough || this._isAllowed ? this._renderChildren() : null;\n }\n\n private _renderChildren() {\n const { children, ability } = this.props;\n const elements = typeof children === 'function'\n ? children(this._isAllowed, ability as any)\n : children;\n\n return elements as ReactNode;\n }\n}\n","import { AnyAbility } from '@casl/ability';\nimport { Consumer, FunctionComponent, createElement } from 'react';\nimport { BoundCanProps, Can } from './Can';\n\nexport function createContextualCan<T extends AnyAbility>(\n Getter: Consumer<T>\n): FunctionComponent<BoundCanProps<T>> {\n return (props: BoundCanProps<T>) => createElement(Getter, {\n children: (ability: T) => \n createElement(Can, { ...props, ability: props.ability || ability } as any),\n });\n}\n","import React from 'react';\nimport { AnyAbility } from '@casl/ability';\n\nexport function useAbility<T extends AnyAbility>(context: React.Context<T>): T {\n const ability = React.useContext<T>(context);\n const [rules, setRules] = React.useState<T['rules']>();\n\n React.useEffect(() => ability.on('updated', (event) => {\n if (event.rules !== rules) {\n setRules(event.rules);\n }\n }), []);\n\n return ability;\n}\n"],"names":["noop","Can","PureComponent","constructor","args","super","this","_isAllowed","_ability","_unsubscribeFromAbility","state","t","componentWillUnmount","_connectToAbility","ability","on","setState","allowed","_canRender","props","subject","of","a","an","can","not","I","do","field","render","passThrough","_renderChildren","children","elements","createContextualCan","Getter","createElement","Object","assign","useAbility","context","React","useContext","rules","setRules","useState","useEffect","event"],"mappings":"4DAWA,MAAMA,EAAOA,OAgCN,MAAMC,UAAkCC,EAA2CC,WAAAA,IAAAC,GAAAC,SAAAD,GAAAE,KAChFC,EAAa,MAAKD,KAClBE,EAAqB,KAAIF,KACzBG,EAAuCT,EAAIM,KACnDI,MAAQ,CAAEC,EAAG,KAAM,CAEnBC,oBAAAA,GACEN,KAAKG,GACP,CAEQI,CAAAA,CAAkBC,GACxB,GAAIA,IAAYR,KAAKE,EACnB,OAGFF,KAAKG,IACLH,KAAKE,EAAW,KAEhB,GAAIM,EAAS,CACXR,KAAKE,EAAWM,EAChBR,KAAKG,EAA0BK,EAAQC,GAAG,WAAW,IAAMT,KAAKU,SAAS,CAAEL,GAAIL,KAAKI,MAAMC,KAC5F,CACF,CAEA,WAAIM,GACF,OAAOX,KAAKC,CACd,CAEQW,CAAAA,GACN,MAAMC,EAAab,KAAKa,MACxB,MAAMC,EAAUD,EAAME,IAAMF,EAAMG,GAAKH,EAAMI,IAAMJ,EAAMb,MAAQa,EAAMJ,GACvE,MAAMS,EAAML,EAAMM,IAAM,SAAW,MAEnC,OAAON,EAAML,QAAQU,GAAKL,EAAMO,GAAKP,EAAMQ,GAAIP,EAASD,EAAMS,MAChE,CAEAC,MAAAA,GACEvB,KAAKO,EAAkBP,KAAKa,MAAML,SAClCR,KAAKC,EAAaD,KAAKY,IACvB,OAAOZ,KAAKa,MAAMW,aAAexB,KAAKC,EAAaD,KAAKyB,IAAoB,IAC9E,CAEQA,CAAAA,GACN,MAAMC,SAAEA,EAAQlB,QAAEA,GAAYR,KAAKa,MACnC,MAAMc,SAAkBD,IAAa,WACjCA,EAAS1B,KAAKC,EAAYO,GAC1BkB,EAEJ,OAAOC,CACT,ECxFK,SAASC,EACdC,GAEA,OAAQhB,GAA4BiB,EAAcD,EAAQ,CACxDH,SAAWlB,GACTsB,EAAcnC,EAAGoC,OAAAC,OAAA,CAAA,EAAOnB,EAAK,CAAEL,QAASK,EAAML,SAAWA,MAE/D,CCRO,SAASyB,WAAiCC,GAC/C,MAAM1B,EAAU2B,EAAMC,WAAcF,GACpC,MAAOG,EAAOC,GAAYH,EAAMI,WAEhCJ,EAAMK,WAAU,IAAMhC,EAAQC,GAAG,WAAYgC,IAC3C,GAAIA,EAAMJ,QAAUA,EAClBC,EAASG,EAAMJ,MACjB,KACE,IAEJ,OAAO7B,CACT"}
@@ -35,10 +35,15 @@ interface BoundCanExtraProps<T extends AnyAbility> extends ExtraProps {
35
35
  }
36
36
  export type CanProps<T extends AnyAbility> = AbilityCanProps<Generics<T>['abilities']> & CanExtraProps<T>;
37
37
  export type BoundCanProps<T extends AnyAbility> = AbilityCanProps<Generics<T>['abilities']> & BoundCanExtraProps<T>;
38
- export declare class Can<T extends AnyAbility, IsBound extends boolean = false> extends PureComponent<IsBound extends true ? BoundCanProps<T> : CanProps<T>> {
38
+ export declare class Can<T extends AnyAbility> extends PureComponent<CanProps<T>, {
39
+ t: boolean;
40
+ }> {
39
41
  private _isAllowed;
40
42
  private _ability;
41
43
  private _unsubscribeFromAbility;
44
+ state: {
45
+ t: boolean;
46
+ };
42
47
  componentWillUnmount(): void;
43
48
  private _connectToAbility;
44
49
  get allowed(): boolean;
@@ -1,9 +1,4 @@
1
- import { ComponentClass, Consumer, FunctionComponent } from 'react';
2
1
  import { AnyAbility } from '@casl/ability';
3
- import { Can, BoundCanProps } from './Can';
4
- interface BoundCanClass<T extends AnyAbility> extends ComponentClass<BoundCanProps<T>> {
5
- new (props: BoundCanProps<T>, context?: any): Can<T, true>;
6
- }
7
- export declare function createCanBoundTo<T extends AnyAbility>(ability: T): BoundCanClass<T>;
2
+ import { Consumer, FunctionComponent } from 'react';
3
+ import { BoundCanProps } from './Can';
8
4
  export declare function createContextualCan<T extends AnyAbility>(Getter: Consumer<T>): FunctionComponent<BoundCanProps<T>>;
9
- export {};
@@ -1,3 +1,3 @@
1
1
  export * from './Can';
2
2
  export * from './factory';
3
- export * from './hooks';
3
+ export * from './hooks/useAbility';
package/dist/umd/index.js CHANGED
@@ -1,2 +1,2 @@
1
- (function(t,n){typeof exports==="object"&&typeof module!=="undefined"?n(exports,require("react")):typeof define==="function"&&define.amd?define(["exports","react"],n):(t=typeof globalThis!=="undefined"?globalThis:t||self,n((t.casl=t.casl||{},t.casl.react={}),t.React))})(this,(function(t,n){"use strict";function r(t,n){if("object"!=typeof t||!t)return t;var r=t[Symbol.toPrimitive];if(void 0!==r){var i=r.call(t,n||"default");if("object"!=typeof i)return i;throw new TypeError("@@toPrimitive must return a primitive value.")}return("string"===n?String:Number)(t)}function i(t){var n=r(t,"string");return"symbol"==typeof n?n:String(n)}function e(t,n){for(var r=0;r<n.length;r++){var e=n[r];e.enumerable=e.enumerable||false;e.configurable=true;if("value"in e)e.writable=true;Object.defineProperty(t,i(e.key),e)}}function u(t,n,r){if(n)e(t.prototype,n);if(r)e(t,r);Object.defineProperty(t,"prototype",{writable:false});return t}function o(){o=Object.assign?Object.assign.bind():function(t){for(var n=1;n<arguments.length;n++){var r=arguments[n];for(var i in r)if(Object.prototype.hasOwnProperty.call(r,i))t[i]=r[i]}return t};return o.apply(this,arguments)}function f(t,n){t.prototype=Object.create(n.prototype);t.prototype.constructor=t;c(t,n)}function c(t,n){c=Object.setPrototypeOf?Object.setPrototypeOf.bind():function t(n,r){n.__proto__=r;return n};return c(t,n)}var s=function t(){};var a=function(t){f(n,t);function n(){var n;for(var r=arguments.length,i=new Array(r),e=0;e<r;e++)i[e]=arguments[e];n=t.call.apply(t,[this].concat(i))||this;n.t=false;n.i=null;n.u=s;return n}var r=n.prototype;r.componentWillUnmount=function t(){this.u()};r.o=function _connectToAbility(t){var n=this;if(t===this.i)return;this.u();this.i=null;if(t){this.i=t;this.u=t.on("updated",(function(){return n.forceUpdate()}))}};r.l=function t(){var n=this.props;var r=n.of||n.a||n.an||n.this||n.on;var i=n.not?"cannot":"can";return n.ability[i](n.I||n.do,r,n.field)};r.render=function t(){this.o(this.props.ability);this.t=this.l();return this.props.passThrough||this.t?this.h():null};r.h=function t(){var n=this.props,r=n.children,i=n.ability;var e=typeof r==="function"?r(this.t,i):r;return e};u(n,[{key:"allowed",get:function t(){return this.t}}]);return n}(n.PureComponent);function l(t){var n;return n=function(t){f(n,t);function n(){return t.apply(this,arguments)||this}return n}(a),n.defaultProps={ability:t},n}function h(t){return function(r){return n.createElement(t,{children:function t(i){return n.createElement(a,o({ability:i},r))}})}}function useAbility(t){if(process.env.NODE_ENV!=="production"&&typeof n.useContext!=="function")throw new Error("You must use React >= 16.8 in order to use useAbility()");var r=n.useContext(t);var i=n.useState(),e=i[0],u=i[1];n.useEffect((function(){return r.on("updated",(function(t){if(t.rules!==e)u(t.rules)}))}),[]);return r}t.Can=a;t.createCanBoundTo=l;t.createContextualCan=h;t.useAbility=useAbility}));
1
+ (function(t,n){typeof exports==="object"&&typeof module!=="undefined"?n(exports,require("react")):typeof define==="function"&&define.amd?define(["exports","react"],n):(t=typeof globalThis!=="undefined"?globalThis:t||self,n((t.casl=t.casl||{},t.casl.react={}),t.React))})(this,(function(t,n){"use strict";function r(t,n){for(var r=0;r<n.length;r++){var i=n[r];i.enumerable=i.enumerable||!1,i.configurable=!0,"value"in i&&(i.writable=!0),Object.defineProperty(t,c(i.key),i)}}function i(t,n,i){return n&&r(t.prototype,n),Object.defineProperty(t,"prototype",{writable:!1}),t}function e(){return e=Object.assign?Object.assign.bind():function(t){for(var n=1;n<arguments.length;n++){var r=arguments[n];for(var i in r)({}).hasOwnProperty.call(r,i)&&(t[i]=r[i])}return t},e.apply(null,arguments)}function u(t,n){t.prototype=Object.create(n.prototype),t.prototype.constructor=t,o(t,n)}function o(t,n){return o=Object.setPrototypeOf?Object.setPrototypeOf.bind():function(t,n){return t.__proto__=n,t},o(t,n)}function f(t,n){if("object"!=typeof t||!t)return t;var r=t[Symbol.toPrimitive];if(void 0!==r){var i=r.call(t,n);if("object"!=typeof i)return i;throw new TypeError("@@toPrimitive must return a primitive value.")}return String(t)}function c(t){var n=f(t,"string");return"symbol"==typeof n?n:n+""}var a=function t(){};var s=function(t){function n(){var n;for(var r=arguments.length,i=new Array(r),e=0;e<r;e++)i[e]=arguments[e];n=t.call.apply(t,[this].concat(i))||this;n.i=false;n.u=null;n.o=a;n.state={t:true};return n}u(n,t);var r=n.prototype;r.componentWillUnmount=function t(){this.o()};r.l=function _connectToAbility(t){var n=this;if(t===this.u)return;this.o();this.u=null;if(t){this.u=t;this.o=t.on("updated",(function(){return n.setState({t:!n.state.t})}))}};r.v=function t(){var n=this.props;var r=n.of||n.a||n.an||n.this||n.on;var i=n.not?"cannot":"can";return n.ability[i](n.I||n.do,r,n.field)};r.render=function t(){this.l(this.props.ability);this.i=this.v();return this.props.passThrough||this.i?this.h():null};r.h=function t(){var n=this.props,r=n.children,i=n.ability;var e=typeof r==="function"?r(this.i,i):r;return e};return i(n,[{key:"allowed",get:function t(){return this.i}}])}(n.PureComponent);function l(t){return function(r){return n.createElement(t,{children:function t(i){return n.createElement(s,e({},r,{ability:r.ability||i}))}})}}function useAbility(t){var r=n.useContext(t);var i=n.useState(),e=i[0],u=i[1];n.useEffect((function(){return r.on("updated",(function(t){if(t.rules!==e)u(t.rules)}))}),[]);return r}t.Can=s;t.createContextualCan=l;t.useAbility=useAbility}));
2
2
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":["../../src/Can.ts","../../src/factory.ts","../../src/hooks/useAbility.ts"],"sourcesContent":["import { PureComponent, ReactNode } from 'react';\nimport {\n Unsubscribe,\n AbilityTuple,\n SubjectType,\n AnyAbility,\n Generics,\n Abilities,\n IfString,\n} from '@casl/ability';\n\nconst noop = () => {};\n\ntype AbilityCanProps<\n T extends Abilities,\n Else = IfString<T, { do: T } | { I: T }>\n> = T extends AbilityTuple\n ? { do: T[0], on: T[1], field?: string } |\n { I: T[0], a: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], an: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], this: Exclude<T[1], SubjectType>, field?: string }\n : Else;\n\ninterface ExtraProps {\n not?: boolean\n passThrough?: boolean\n}\n\ninterface CanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\ninterface BoundCanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability?: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\nexport type CanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & CanExtraProps<T>;\nexport type BoundCanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & BoundCanExtraProps<T>;\n\nexport class Can<\n T extends AnyAbility,\n IsBound extends boolean = false\n> extends PureComponent<IsBound extends true ? BoundCanProps<T> : CanProps<T>> {\n private _isAllowed: boolean = false;\n private _ability: T | null = null;\n private _unsubscribeFromAbility: Unsubscribe = noop;\n\n componentWillUnmount() {\n this._unsubscribeFromAbility();\n }\n\n private _connectToAbility(ability?: T) {\n if (ability === this._ability) {\n return;\n }\n\n this._unsubscribeFromAbility();\n this._ability = null;\n\n if (ability) {\n this._ability = ability;\n this._unsubscribeFromAbility = ability.on('updated', () => this.forceUpdate());\n }\n }\n\n get allowed() {\n return this._isAllowed;\n }\n\n private _canRender(): boolean {\n const props: any = this.props;\n const subject = props.of || props.a || props.an || props.this || props.on;\n const can = props.not ? 'cannot' : 'can';\n\n return props.ability[can](props.I || props.do, subject, props.field);\n }\n\n render() {\n this._connectToAbility(this.props.ability);\n this._isAllowed = this._canRender();\n return this.props.passThrough || this._isAllowed ? this._renderChildren() : null;\n }\n\n private _renderChildren() {\n const { children, ability } = this.props;\n const elements = typeof children === 'function'\n ? children(this._isAllowed, ability as any)\n : children;\n\n return elements as ReactNode;\n }\n}\n","import { createElement as h, ComponentClass, Consumer, FunctionComponent } from 'react';\nimport { AnyAbility } from '@casl/ability';\nimport { Can, BoundCanProps } from './Can';\n\ninterface BoundCanClass<T extends AnyAbility> extends ComponentClass<BoundCanProps<T>> {\n new (props: BoundCanProps<T>, context?: any): Can<T, true>\n}\n\nexport function createCanBoundTo<T extends AnyAbility>(ability: T): BoundCanClass<T> {\n return class extends Can<T, true> {\n static defaultProps = { ability } as BoundCanClass<T>['defaultProps'];\n };\n}\n\nexport function createContextualCan<T extends AnyAbility>(\n Getter: Consumer<T>\n): FunctionComponent<BoundCanProps<T>> {\n return (props: BoundCanProps<T>) => h(Getter, {\n children: (ability: T) => h(Can, {\n ability,\n ...props,\n } as any)\n });\n}\n","import React from 'react';\nimport { AnyAbility } from '@casl/ability';\n\nexport function useAbility<T extends AnyAbility>(context: React.Context<T>): T {\n if (process.env.NODE_ENV !== 'production' && typeof React.useContext !== 'function') {\n /* istanbul ignore next */\n throw new Error('You must use React >= 16.8 in order to use useAbility()');\n }\n\n const ability = React.useContext<T>(context);\n const [rules, setRules] = React.useState<T['rules']>();\n\n React.useEffect(() => ability.on('updated', (event) => {\n if (event.rules !== rules) {\n setRules(event.rules);\n }\n }), []);\n\n return ability;\n}\n"],"names":["noop","Can","_PureComponent","_inheritsLoose","_this","_len","arguments","length","args","Array","_key","call","apply","this","concat","_isAllowed","_ability","_unsubscribeFromAbility","_proto","prototype","componentWillUnmount","_connectToAbility","ability","_this2","on","forceUpdate","_canRender","props","subject","of","a","an","can","not","I","do","field","render","passThrough","_renderChildren","_this$props","children","elements","_createClass","key","get","PureComponent","createCanBoundTo","_Class","_Can","defaultProps","createContextualCan","Getter","h","createElement","_extends","useAbility","context","process","env","NODE_ENV","React","useContext","Error","_React$useState","useState","rules","setRules","useEffect","event"],"mappings":"q1CAWA,IAAMA,EAAO,SAAPA,MAgCOC,IAAAA,WAAGC,GAAAC,EAAAF,EAAAC,GAAA,SAAAD,IAAA,IAAAG,EAAA,IAAA,IAAAC,EAAAC,UAAAC,OAAAC,EAAAC,IAAAA,MAAAJ,GAAAK,EAAA,EAAAA,EAAAL,EAAAK,IAAAF,EAAAE,GAAAJ,UAAAI,GAAAN,EAAAF,EAAAS,KAAAC,MAAAV,EAAA,CAAAW,MAAAC,OAAAN,KAAAK,KAAAT,EAINW,EAAsB,MAAKX,EAC3BY,EAAqB,KAAIZ,EACzBa,EAAuCjB,EAAI,OAAAI,CAAA,CAAA,IAAAc,EAAAjB,EAAAkB,UAAAD,EAEnDE,qBAAA,SAAAA,IACEP,KAAKI,KACNC,EAEOG,EAAR,SAAAA,kBAA0BC,GAAa,IAAAC,EAAAV,KACrC,GAAIS,IAAYT,KAAKG,EACnB,OAGFH,KAAKI,IACLJ,KAAKG,EAAW,KAEhB,GAAIM,EAAS,CACXT,KAAKG,EAAWM,EAChBT,KAAKI,EAA0BK,EAAQE,GAAG,WAAW,WAAA,OAAMD,EAAKE,gBAClE,GACDP,EAMOQ,EAAR,SAAAA,IACE,IAAMC,EAAad,KAAKc,MACxB,IAAMC,EAAUD,EAAME,IAAMF,EAAMG,GAAKH,EAAMI,IAAMJ,EAAMd,MAAQc,EAAMH,GACvE,IAAMQ,EAAML,EAAMM,IAAM,SAAW,MAEnC,OAAON,EAAML,QAAQU,GAAKL,EAAMO,GAAKP,EAAMQ,GAAIP,EAASD,EAAMS,QAC/DlB,EAEDmB,OAAA,SAAAA,IACExB,KAAKQ,EAAkBR,KAAKc,MAAML,SAClCT,KAAKE,EAAaF,KAAKa,IACvB,OAAOb,KAAKc,MAAMW,aAAezB,KAAKE,EAAaF,KAAK0B,IAAoB,MAC7ErB,EAEOqB,EAAR,SAAAA,IACE,IAAAC,EAA8B3B,KAAKc,MAA3Bc,EAAQD,EAARC,SAAUnB,EAAOkB,EAAPlB,QAClB,IAAMoB,SAAkBD,IAAa,WACjCA,EAAS5B,KAAKE,EAAYO,GAC1BmB,EAEJ,OAAOC,GACRC,EAAA1C,EAAA,CAAA,CAAA2C,IAAA,UAAAC,IAzBD,SAAAA,IACE,OAAOhC,KAAKE,CACd,KAAC,OAAAd,CAAA,EAzBO6C,EAAaA,eCtChB,SAASC,EAAuCzB,GAA8B,IAAA0B,EACnF,OAAAA,WAAAC,GAAA9C,EAAA6C,EAAAC,GAAA,SAAAD,IAAA,OAAAC,EAAArC,MAAAC,KAAAP,YAAAO,IAAA,CAAA,OAAAmC,CAAA,EAAqB/C,GAAG+C,EACfE,aAAe,CAAE5B,QAAAA,GAAS0B,CAErC,CAEO,SAASG,EACdC,GAEA,OAAO,SAACzB,GAAuB,OAAK0B,EAAAA,cAAED,EAAQ,CAC5CX,SAAU,SAAAA,EAACnB,GAAU,OAAK+B,EAACC,cAACrD,EAAGsD,EAAA,CAC7BjC,QAAAA,GACGK,GACI,GACT,CACJ,CCpBO,SAAS6B,WAAiCC,GAC/C,GAAIC,QAAQC,IAAIC,WAAa,qBAAuBC,EAAMC,aAAe,WAEvE,MAAM,IAAIC,MAAM,2DAGlB,IAAMzC,EAAUuC,EAAMC,WAAcL,GACpC,IAAAO,EAA0BH,EAAMI,WAAzBC,EAAKF,EAAA,GAAEG,EAAQH,EAAA,GAEtBH,EAAMO,WAAU,WAAA,OAAM9C,EAAQE,GAAG,WAAW,SAAC6C,GAC3C,GAAIA,EAAMH,QAAUA,EAClBC,EAASE,EAAMH,MAEnB,GAAE,GAAE,IAEJ,OAAO5C,CACT"}
1
+ {"version":3,"file":"index.js","sources":["../../src/Can.ts","../../src/factory.ts","../../src/hooks/useAbility.ts"],"sourcesContent":["import { PureComponent, ReactNode } from 'react';\nimport {\n Unsubscribe,\n AbilityTuple,\n SubjectType,\n AnyAbility,\n Generics,\n Abilities,\n IfString,\n} from '@casl/ability';\n\nconst noop = () => {};\n\ntype AbilityCanProps<\n T extends Abilities,\n Else = IfString<T, { do: T } | { I: T }>\n> = T extends AbilityTuple\n ? { do: T[0], on: T[1], field?: string } |\n { I: T[0], a: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], an: Extract<T[1], SubjectType>, field?: string } |\n { I: T[0], this: Exclude<T[1], SubjectType>, field?: string }\n : Else;\n\ninterface ExtraProps {\n not?: boolean\n passThrough?: boolean\n}\n\ninterface CanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\ninterface BoundCanExtraProps<T extends AnyAbility> extends ExtraProps {\n ability?: T\n children: ReactNode | ((isAllowed: boolean, ability: T) => ReactNode)\n}\n\nexport type CanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & CanExtraProps<T>;\nexport type BoundCanProps<T extends AnyAbility> =\n AbilityCanProps<Generics<T>['abilities']> & BoundCanExtraProps<T>;\n\nexport class Can<T extends AnyAbility> extends PureComponent<CanProps<T>, { t: boolean }> {\n private _isAllowed = false;\n private _ability: T | null = null;\n private _unsubscribeFromAbility: Unsubscribe = noop;\n state = { t: true }\n\n componentWillUnmount() {\n this._unsubscribeFromAbility();\n }\n\n private _connectToAbility(ability?: T) {\n if (ability === this._ability) {\n return;\n }\n\n this._unsubscribeFromAbility();\n this._ability = null;\n\n if (ability) {\n this._ability = ability;\n this._unsubscribeFromAbility = ability.on('updated', () => this.setState({ t: !this.state.t }));\n }\n }\n\n get allowed() {\n return this._isAllowed;\n }\n\n private _canRender(): boolean {\n const props: any = this.props;\n const subject = props.of || props.a || props.an || props.this || props.on;\n const can = props.not ? 'cannot' : 'can';\n\n return props.ability[can](props.I || props.do, subject, props.field);\n }\n\n render() {\n this._connectToAbility(this.props.ability);\n this._isAllowed = this._canRender();\n return this.props.passThrough || this._isAllowed ? this._renderChildren() : null;\n }\n\n private _renderChildren() {\n const { children, ability } = this.props;\n const elements = typeof children === 'function'\n ? children(this._isAllowed, ability as any)\n : children;\n\n return elements as ReactNode;\n }\n}\n","import { AnyAbility } from '@casl/ability';\nimport { Consumer, FunctionComponent, createElement } from 'react';\nimport { BoundCanProps, Can } from './Can';\n\nexport function createContextualCan<T extends AnyAbility>(\n Getter: Consumer<T>\n): FunctionComponent<BoundCanProps<T>> {\n return (props: BoundCanProps<T>) => createElement(Getter, {\n children: (ability: T) => \n createElement(Can, { ...props, ability: props.ability || ability } as any),\n });\n}\n","import React from 'react';\nimport { AnyAbility } from '@casl/ability';\n\nexport function useAbility<T extends AnyAbility>(context: React.Context<T>): T {\n const ability = React.useContext<T>(context);\n const [rules, setRules] = React.useState<T['rules']>();\n\n React.useEffect(() => ability.on('updated', (event) => {\n if (event.rules !== rules) {\n setRules(event.rules);\n }\n }), []);\n\n return ability;\n}\n"],"names":["noop","Can","_PureComponent","_this","_len","arguments","length","args","Array","_key","call","apply","this","concat","_isAllowed","_ability","_unsubscribeFromAbility","state","t","_inheritsLoose","_proto","prototype","componentWillUnmount","_connectToAbility","ability","_this2","on","setState","_canRender","props","subject","of","a","an","can","not","I","do","field","render","passThrough","_renderChildren","_this$props","children","elements","_createClass","key","get","PureComponent","createContextualCan","Getter","createElement","_extends","useAbility","context","React","useContext","_React$useState","useState","rules","setRules","useEffect","event"],"mappings":"0wCAWA,IAAMA,EAAO,SAAPA,MAgCOC,IAAAA,WAAGC,GAAA,SAAAD,IAAA,IAAAE,EAAA,IAAA,IAAAC,EAAAC,UAAAC,OAAAC,EAAAC,IAAAA,MAAAJ,GAAAK,EAAA,EAAAA,EAAAL,EAAAK,IAAAF,EAAAE,GAAAJ,UAAAI,GAAAN,EAAAD,EAAAQ,KAAAC,MAAAT,EAAA,CAAAU,MAAAC,OAAAN,KAAAK,KAAAT,EACNW,EAAa,MAAKX,EAClBY,EAAqB,KAAIZ,EACzBa,EAAuChB,EAAIG,EACnDc,MAAQ,CAAEC,EAAG,MAAM,OAAAf,CAAA,CAAAgB,EAAAlB,EAAAC,GAAA,IAAAkB,EAAAnB,EAAAoB,UAAAD,EAEnBE,qBAAA,SAAAA,IACEV,KAAKI,KACNI,EAEOG,EAAR,SAAQA,kBAAkBC,GAAa,IAAAC,EAAAb,KACrC,GAAIY,IAAYZ,KAAKG,EACnB,OAGFH,KAAKI,IACLJ,KAAKG,EAAW,KAEhB,GAAIS,EAAS,CACXZ,KAAKG,EAAWS,EAChBZ,KAAKI,EAA0BQ,EAAQE,GAAG,WAAW,WAAA,OAAMD,EAAKE,SAAS,CAAET,GAAIO,EAAKR,MAAMC,MAC5F,GACDE,EAMOQ,EAAR,SAAQA,IACN,IAAMC,EAAajB,KAAKiB,MACxB,IAAMC,EAAUD,EAAME,IAAMF,EAAMG,GAAKH,EAAMI,IAAMJ,EAAMjB,MAAQiB,EAAMH,GACvE,IAAMQ,EAAML,EAAMM,IAAM,SAAW,MAEnC,OAAON,EAAML,QAAQU,GAAKL,EAAMO,GAAKP,EAAMQ,GAAIP,EAASD,EAAMS,QAC/DlB,EAEDmB,OAAA,SAAAA,IACE3B,KAAKW,EAAkBX,KAAKiB,MAAML,SAClCZ,KAAKE,EAAaF,KAAKgB,IACvB,OAAOhB,KAAKiB,MAAMW,aAAe5B,KAAKE,EAAaF,KAAK6B,IAAoB,MAC7ErB,EAEOqB,EAAR,SAAQA,IACN,IAAAC,EAA8B9B,KAAKiB,MAA3Bc,EAAQD,EAARC,SAAUnB,EAAOkB,EAAPlB,QAClB,IAAMoB,SAAkBD,IAAa,WACjCA,EAAS/B,KAAKE,EAAYU,GAC1BmB,EAEJ,OAAOC,GACR,OAAAC,EAAA5C,EAAA,CAAA,CAAA6C,IAAA,UAAAC,IAzBD,SAAAA,IACE,OAAOnC,KAAKE,CACd,IAAC,EA1B4CkC,EAAaA,eCvCrD,SAASC,EACdC,GAEA,OAAO,SAACrB,GAAuB,OAAKsB,EAAAA,cAAcD,EAAQ,CACxDP,SAAU,SAAVA,EAAWnB,GAAU,OACnB2B,EAAaA,cAAClD,EAAGmD,KAAOvB,EAAK,CAAEL,QAASK,EAAML,SAAWA,IAAiB,GAC5E,CACJ,CCRO,SAAS6B,WAAiCC,GAC/C,IAAM9B,EAAU+B,EAAMC,WAAcF,GACpC,IAAAG,EAA0BF,EAAMG,WAAzBC,EAAKF,EAAA,GAAEG,EAAQH,EAAA,GAEtBF,EAAMM,WAAU,WAAA,OAAMrC,EAAQE,GAAG,WAAW,SAACoC,GAC3C,GAAIA,EAAMH,QAAUA,EAClBC,EAASE,EAAMH,MAEnB,GAAE,GAAE,IAEJ,OAAOnC,CACT"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@casl/react",
3
- "version": "4.0.0",
3
+ "version": "5.0.0",
4
4
  "description": "React component for CASL which makes it easy to add permissions in any React application",
5
5
  "main": "dist/umd/index.js",
6
6
  "module": "dist/es5m/index.js",
@@ -23,13 +23,13 @@
23
23
  "access": "public"
24
24
  },
25
25
  "scripts": {
26
- "prebuild": "rm -rf dist/* && npm run build.types",
27
- "build": "BUILD_TYPES=es5m,es6m,umd dx rollup -n casl.react -g react:React,prop-types:React.PropTypes,@casl/ability:casl",
26
+ "build.prepare": "rm -rf dist/* && npm run build.types",
27
+ "build": "npm run build.prepare && BUILD_TYPES=es5m,es6m,umd dx rollup -n casl.react -g react:React,prop-types:React.PropTypes,@casl/ability:casl",
28
28
  "build.types": "dx tsc",
29
29
  "lint": "dx eslint src/ spec/",
30
- "test": "dx jest --env jsdom --config ../dx/config/jest.chai.config.js",
31
- "prerelease": "npm run lint && npm test && NODE_ENV=production npm run build",
32
- "release": "dx semantic-release"
30
+ "test": "dx jest --env jsdom",
31
+ "release.prepare": "npm run lint && npm test && NODE_ENV=production npm run build",
32
+ "release": "npm run release.prepare && dx semantic-release"
33
33
  },
34
34
  "keywords": [
35
35
  "casl",
@@ -41,20 +41,21 @@
41
41
  "author": "Sergii Stotskyi <sergiy.stotskiy@gmail.com>",
42
42
  "license": "MIT",
43
43
  "peerDependencies": {
44
- "@casl/ability": "^3.0.0 || ^4.0.0 || ^5.1.0 || ^6.0.0",
45
- "react": "^16.0.0 || ^17.0.0 || ^18.0.0"
44
+ "@casl/ability": "^4.0.0 || ^5.1.0 || ^6.0.0",
45
+ "react": "^17.0.0 || ^18.0.0 || ^19.0.0"
46
46
  },
47
47
  "devDependencies": {
48
48
  "@casl/ability": "^6.0.0",
49
49
  "@casl/dx": "workspace:^1.0.0",
50
- "@testing-library/react-hooks": "^4.0.1",
50
+ "@testing-library/dom": "^10.4.0",
51
+ "@testing-library/react": "^16.1.0",
51
52
  "@types/jest": "^29.0.0",
52
- "@types/node": "^20.0.0",
53
- "@types/react": "^18.0.0",
53
+ "@types/node": "^22.0.0",
54
+ "@types/react": "^19.0.0",
54
55
  "chai": "^4.1.0",
55
56
  "chai-spies": "^1.0.0",
56
- "react": "^18.0.0",
57
- "react-test-renderer": "^18.0.0"
57
+ "react": "^19.0.0",
58
+ "react-dom": "^19.0.0"
58
59
  },
59
60
  "files": [
60
61
  "dist",
@@ -1 +0,0 @@
1
- export * from './useAbility';