Skip to content

Commit

Permalink
Merge pull request #580 from uploadcare/feat/events-refactor
Browse files Browse the repository at this point in the history
Better events
  • Loading branch information
nd0ut authored Feb 5, 2024
2 parents e9d84a2 + b888e8e commit 1a510d9
Show file tree
Hide file tree
Showing 80 changed files with 2,834 additions and 2,055 deletions.
12 changes: 12 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,15 @@
## [unreleased]

### Breaking changes

- Global events are removed. I.e. `window.addEventListener('LR_UPLOAD_FINISH', ...)` will not work anymore. Now you need to use `lr-upload-ctx-provider` block to subscribe to the events. See the [documentation](#) for more details.
- All existing events and their payloads are changed. See the [documentation](#) for more details.
- `lr-data-output` block is removed.
- To handle HTML forms you need to use `lr-form-input` block.
- Groups output moved to the `lr-upload-ctx-provider` events
- Console debugging output now enabled with the `debug` attribute on `lr-config`
- `lr-message-box` block is removed.

## [0.31.1](https://github.com/uploadcare/blocks/compare/v0.31.0...v0.31.1) (2024-01-30)

### Bug Fixes
Expand Down
10 changes: 7 additions & 3 deletions abstract/ActivityBlock.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
// @ts-check
import { debounce } from '../blocks/utils/debounce.js';
import { EventType } from '../blocks/UploadCtxProvider/EventEmitter.js';
import { Block } from './Block.js';
import { activityBlockCtx } from './CTX.js';

Expand All @@ -19,7 +20,6 @@ export class ActivityBlock extends Block {
this[ACTIVE_PROP] = false;
this.removeAttribute(ACTIVE_ATTR);
actDesc?.deactivateCallback?.();
// console.log(`Activity "${this.activityType}" deactivated`);
}

/** @private */
Expand All @@ -31,9 +31,12 @@ export class ActivityBlock extends Block {
this[ACTIVE_PROP] = true;
this.setAttribute(ACTIVE_ATTR, '');
actDesc?.activateCallback?.();
// console.log(`Activity "${this.activityType}" activated`);

this._debouncedHistoryFlush();

this.emit(EventType.ACTIVITY_CHANGE, {
activity: this.activityType,
});
}

initCallback() {
Expand Down Expand Up @@ -186,7 +189,6 @@ export class ActivityBlock extends Block {
}
}

/** @enum {String} */
ActivityBlock.activities = Object.freeze({
START_FROM: 'start-from',
CAMERA: 'camera',
Expand All @@ -198,3 +200,5 @@ ActivityBlock.activities = Object.freeze({
EXTERNAL: 'external',
DETAILS: 'details',
});

/** @typedef {(typeof ActivityBlock)['activities'][keyof (typeof ActivityBlock)['activities']] | null} ActivityType */
43 changes: 29 additions & 14 deletions abstract/Block.js
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@ export class Block extends BaseComponent {
static className = '';
requireCtxName = false;
allowCustomTemplate = true;
/** @type {import('./ActivityBlock.js').ActivityType} */
activityType = null;

init$ = blockCtx();

Expand All @@ -37,7 +39,7 @@ export class Block extends BaseComponent {
for (let pluralObject of pluralObjects) {
variables[pluralObject.variable] = this.pluralize(
pluralObject.pluralKey,
Number(variables[pluralObject.countVariable])
Number(variables[pluralObject.countVariable]),
);
}
let result = applyTemplateData(template, variables);
Expand All @@ -57,9 +59,6 @@ export class Block extends BaseComponent {

constructor() {
super();
/** @type {String} */
// @ts-ignore TODO: fix this
this.activityType = null;
// @ts-ignore TODO: fix this
this.addTemplateProcessor(l10nProcessor);
// TODO: inspect template on lr-* elements
Expand All @@ -79,10 +78,9 @@ export class Block extends BaseComponent {
}

/**
* @template {typeof import('../blocks/UploadCtxProvider/EventEmitter.js').EventType[keyof typeof import('../blocks/UploadCtxProvider/EventEmitter.js').EventType]} T
* @param {T} type
* @param {import('../blocks/UploadCtxProvider/EventEmitter.js').EventPayload[T]} [payload]
* @param {{ debounce?: boolean | number }} [options]
* @param {Parameters<import('../blocks/UploadCtxProvider/EventEmitter.js').EventEmitter['emit']>[0]} type
* @param {Parameters<import('../blocks/UploadCtxProvider/EventEmitter.js').EventEmitter['emit']>[1]} [payload]
* @param {Parameters<import('../blocks/UploadCtxProvider/EventEmitter.js').EventEmitter['emit']>[2]} [options]
*/
emit(type, payload, options) {
/** @type {import('../blocks/UploadCtxProvider/EventEmitter.js').EventEmitter} */
Expand Down Expand Up @@ -128,11 +126,11 @@ export class Block extends BaseComponent {
{
[prop]: newVal,
},
true
true,
);
}

/** @param {String} activityType */
/** @param {import('./ActivityBlock.js').ActivityType} activityType */
setActivity(activityType) {
if (this.hasBlockInCtx((b) => b.activityType === activityType)) {
this.$['*currentActivity'] = activityType;
Expand Down Expand Up @@ -182,7 +180,7 @@ export class Block extends BaseComponent {
blocksRegistry.add(this);

if (!this.$['*eventEmitter']) {
this.$['*eventEmitter'] = new EventEmitter(() => this.ctxName);
this.$['*eventEmitter'] = new EventEmitter(this.debugPrint.bind(this));
}
}

Expand Down Expand Up @@ -246,7 +244,7 @@ export class Block extends BaseComponent {
return applyTemplateData(
previewProxy,
{ previewUrl: url },
{ transform: (value) => window.encodeURIComponent(value) }
{ transform: (value) => window.encodeURIComponent(value) },
);
}

Expand Down Expand Up @@ -286,7 +284,7 @@ export class Block extends BaseComponent {
return parsed.ctx.read(parsed.name);
} else {
warnOnce(
'Using CSS variables for configuration is deprecated. Please use `lr-config` instead. See migration guide: https://uploadcare.com/docs/file-uploader/migration-to-0.25.0/'
'Using CSS variables for configuration is deprecated. Please use `lr-config` instead. See migration guide: https://uploadcare.com/docs/file-uploader/migration-to-0.25.0/',
);
return this.getCssData(`--cfg-${toKebabCase(key)}`);
}
Expand Down Expand Up @@ -314,7 +312,7 @@ export class Block extends BaseComponent {
/** @deprecated */
updateCtxCssData = () => {
warnOnce(
'Using CSS variables for configuration is deprecated. Please use `lr-config` instead. See migration guide: https://uploadcare.com/docs/file-uploader/migration-to-0.25.0/'
'Using CSS variables for configuration is deprecated. Please use `lr-config` instead. See migration guide: https://uploadcare.com/docs/file-uploader/migration-to-0.25.0/',
);

/** @type {Set<Block>} */
Expand All @@ -326,6 +324,23 @@ export class Block extends BaseComponent {
}
};

/** @param {unknown[]} args */
debugPrint(...args) {
if (!this.cfg.debug) {
return;
}
let consoleArgs = args;
if (typeof args?.[0] === 'function') {
const resolver = args[0];
consoleArgs = resolver();
}
console.log(`[${this.debugCtxName}]`, ...consoleArgs);
}

get debugCtxName() {
return this.ctxName;
}

/** @param {String} [name] */
static reg(name) {
if (!name) {
Expand Down
8 changes: 7 additions & 1 deletion abstract/CTX.js
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,15 @@ export const uploaderBlockCtx = (fnCtx) => ({
...activityBlockCtx(fnCtx),
'*commonProgress': 0,
'*uploadList': [],
'*outputData': null,
'*focusedEntry': null,
'*uploadMetadata': null,
'*uploadQueue': new Queue(1),
'*uploadCollection': null,
/** @type {ReturnType<import('../utils/buildOutputError.js').buildCollectionFileError>[]} */
'*collectionErrors': [],
/** @type {import('../types').OutputCollectionState | null} */
'*collectionState': null,
/** @type {import('@uploadcare/upload-client').UploadcareGroup | null} */
'*groupInfo': null,
'*uploadTrigger': null,
});
16 changes: 10 additions & 6 deletions abstract/TypedCollection.js
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,10 @@ export class TypedCollection {
/** @param {(list: string[], added: Set<any>, removed: Set<any>) => void} handler */
observeCollection(handler) {
this.__collectionObservers.add(handler);
this.notify();

if (this.__items.size > 0) {
this.notify();
}

return () => {
this.unobserveCollection(handler);
Expand All @@ -122,13 +125,16 @@ export class TypedCollection {

/**
* @param {Object<string, any>} init
* @returns {any}
* @returns {string}
*/
add(init) {
let item = new TypedData(this.__typedSchema);
for (let prop in init) {
item.setValue(prop, init[prop]);
}
this.__items.add(item.uid);
this.notify();

this.__data.add(item.uid, item);
this.__added.add(item);
this.__watchList.forEach((propName) => {
Expand All @@ -138,12 +144,10 @@ export class TypedCollection {
this.__subsMap[item.uid].push(
item.subscribe(propName, () => {
this.__notifyObservers(propName, item.uid);
})
}),
);
});
this.__items.add(item.uid);
this.notify();
return item;
return item.uid;
}

/**
Expand Down
Loading

0 comments on commit 1a510d9

Please sign in to comment.