Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Release v1.6 #219

Merged
merged 77 commits into from
Sep 26, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
77 commits
Select commit Hold shift + click to select a range
b0d6eef
[movex-master] WIP - Add reducer.$transformState feature
GabrielCTroia Jul 16, 2024
057d86a
[movex-master, movex] Refactor MovexResourceObservable.getUncheckedSt…
GabrielCTroia Jul 17, 2024
1358c65
[movex-master] Test the "reducer.$transformState" functionality more …
GabrielCTroia Jul 17, 2024
2fc5f8f
chore(libs): :hammer: [libs] Add the "tsc" script to all the libs tha…
GabrielCTroia Jul 17, 2024
e0347fc
feat(libs/movex-react-local-master): :sparkles: add storybook to test…
GabrielCTroia Jul 17, 2024
48fa69b
test($stateTransformer feat): :white_check_mark: Add a story to test …
GabrielCTroia Jul 18, 2024
d3eadf9
fix(movex-react-local-master): :bug: fix the SpeedPushGame story
GabrielCTroia Jul 20, 2024
f629515
chore(version): :hammer: bump to v0.1.6-0 - Add $transformState feature
GabrielCTroia Jul 23, 2024
a6d522f
fix(movex-server): :bug: add a new api resource to server the resourc…
GabrielCTroia Jul 23, 2024
103c6a2
fix(movex-server): :bug: add a new api resource to serve public state…
GabrielCTroia Jul 23, 2024
62ce435
fix(movex-master, movex-server, movex-store): :bug: fix the ability t…
GabrielCTroia Jul 25, 2024
e7f3ef4
chore(publisable-libs): :hammer: bump version to 0.1.6-2
GabrielCTroia Jul 25, 2024
0be4586
fix(Movex-master): :bug: take out debugging console.logs
GabrielCTroia Jul 30, 2024
0b37a38
feat(movex-core-util): :sparkles: add "MovexDispatchOf" type
GabrielCTroia Aug 17, 2024
f79ca48
refactor([movex-core-utils]): :recycle: strengthen the "isAction" inp…
GabrielCTroia Aug 18, 2024
0756c57
Merge pull request #218 from movesthatmatter/add-state-transformer
GabrielCTroia Aug 18, 2024
40529ee
Merge pull request #217 from movesthatmatter/add-storybook
GabrielCTroia Aug 18, 2024
63763c7
feat(movex-master, movex): :sparkles: wIP - First draft of masterActi…
GabrielCTroia Aug 18, 2024
64a4d86
test(movex-react-local-master, movex-master): :white_check_mark: add …
GabrielCTroia Aug 18, 2024
bba2490
ci(publishable-libs): :ferris_wheel: bump to v0.1.6-3
GabrielCTroia Aug 18, 2024
9e2216c
0.1.6-3
GabrielCTroia Aug 18, 2024
bb882b6
test(movex-master, movex-core-util): :white_check_mark: add tests for…
GabrielCTroia Aug 19, 2024
60d04d7
ci(publishable-libs): :ferris_wheel: bump to v0.1.6-4
GabrielCTroia Aug 19, 2024
777d560
fix(movex): :bug: movexResource.get returning different response than…
GabrielCTroia Aug 21, 2024
695d6c9
ci(movex-lib): :ferris_wheel: bump to v0.1.6-5
GabrielCTroia Aug 21, 2024
b8ec6f8
ci(publishable-libs): :ferris_wheel: bump to 0.1.6-5
GabrielCTroia Aug 21, 2024
931743b
feat(movex-service): :sparkles: add log with the version number
GabrielCTroia Aug 22, 2024
0d408d3
ci(movex-service): :ferris_wheel: make the dependencies on other move…
GabrielCTroia Aug 22, 2024
e0b7ac7
fix(movex-service): :bug: switch back to dependencies from peerDepend…
GabrielCTroia Aug 22, 2024
438093d
fix(movex-service): :bug: fix the path to package.json
GabrielCTroia Aug 22, 2024
b621db0
feat(movex-master, movex-service, movex-server): :sparkles: add abili…
GabrielCTroia Aug 22, 2024
f010799
ci(publishable-libs): :ferris_wheel: v0.1.6-10
GabrielCTroia Aug 22, 2024
76727e4
refactor(movex-master, movex, movex-core-util): :recycle: move the Co…
GabrielCTroia Aug 22, 2024
f76f968
refactor(movex-core-util): :recycle: organize the event emitter relat…
GabrielCTroia Aug 22, 2024
32f7f3a
feat(io): :sparkles: add "disconnect" & "connectionError" states, so …
GabrielCTroia Aug 22, 2024
c3adc91
ci(publishable-libs): :ferris_wheel: v0.1.6-23
GabrielCTroia Aug 22, 2024
c80e931
docs(all): :memo: start a changelog
GabrielCTroia Aug 22, 2024
2a09b8b
feat(movex, movex-master, movex-server): :sparkles: wIP - Add a way t…
GabrielCTroia Aug 23, 2024
4bc25d4
fix(movex): :bug: fwdAction Checksum Mismatch wasn't calling resync s…
GabrielCTroia Aug 27, 2024
db6525c
ci(libs): :ferris_wheel: bump to v0.1.6-37
GabrielCTroia Aug 27, 2024
d5eb8da
fix(movex-server): :bug: wIP - Attempt to provide a way to call the $…
GabrielCTroia Aug 27, 2024
fe50959
fix(movex-master): :bug: fix failing tests introduced w/ to clockOffs…
GabrielCTroia Aug 28, 2024
dd46350
fix(movex-react): :bug: fix failing test introduced when changing the…
GabrielCTroia Aug 28, 2024
6201f4f
feat(movex-master): :sparkles: wIP - add movexMasterContext.requestAt…
GabrielCTroia Aug 28, 2024
48b8940
0.1.6-38
GabrielCTroia Aug 28, 2024
9053510
Bump to v0.1.6-40
GabrielCTroia Aug 28, 2024
624585a
fix(movex-master, movex-service): :bug: add logs with the version dis…
GabrielCTroia Aug 28, 2024
1706fcc
refactor(movex-master): :recycle: wIP - take out clock offset logs. A…
GabrielCTroia Aug 28, 2024
dc4eb4f
Bump to v0.1.6-42
GabrielCTroia Aug 28, 2024
0d9690a
refactor(movex-master, movex-server): :recycle: temporary - Add extra…
GabrielCTroia Aug 28, 2024
b29668d
fix(movex-master): :bug: attempt to show the movex-master version onc…
GabrielCTroia Aug 28, 2024
2bb2518
Bump to v0.1.6-44
GabrielCTroia Aug 28, 2024
20ba97c
fix(movex-master): :bug: take out unneded console.trace and attempt t…
GabrielCTroia Aug 28, 2024
b28afd5
Bump to v0.1.6-45
GabrielCTroia Aug 28, 2024
26305e1
WIP - Added the idea that the stateTransformer can run on local as lo…
GabrielCTroia Aug 28, 2024
ff2dd80
fix(movex-master, movex): :bug: add tests and fix issue between apply…
GabrielCTroia Aug 30, 2024
e74906e
fix(movex): :bug: fix circular dependency
GabrielCTroia Aug 30, 2024
83c9797
0.1.6-51
GabrielCTroia Aug 30, 2024
a644792
test(masterActions & stateTransformers): :white_check_mark: wIP - sta…
GabrielCTroia Sep 5, 2024
47c2545
Bump to v0.1.6-57
GabrielCTroia Sep 5, 2024
f0a00f9
fix(movex-master): :bug: fix tests
GabrielCTroia Sep 5, 2024
0336d7b
docs(changelog): :memo: append the latest to changelog
GabrielCTroia Sep 5, 2024
0490a01
refactor(movex): :recycle: take out unneded code, comments, logs, and…
GabrielCTroia Sep 5, 2024
dab4a3e
refactor(movex): :recycle: start Using the MovexContext for MasterAct…
GabrielCTroia Sep 5, 2024
ea71e9d
refactor(clock-offset): :recycle: take out the feature of "clock-offs…
GabrielCTroia Sep 5, 2024
622946e
refactor(movex): :recycle: use shortlink in MovexResource log
GabrielCTroia Sep 5, 2024
6e3a0fb
ci(all-libs): :ferris_wheel: bump to v0.1.6-58
GabrielCTroia Sep 5, 2024
ca02917
Merge pull request #222 from movesthatmatter/optimize-size
GabrielCTroia Sep 26, 2024
2c79bf8
Merge pull request #220 from movesthatmatter/improve-connection-events
GabrielCTroia Sep 26, 2024
d26db7d
Merge pull request #216 from movesthatmatter/add-master-actions
GabrielCTroia Sep 26, 2024
f745354
Merge pull request #223 from movesthatmatter/fix-state-transformer
GabrielCTroia Sep 26, 2024
0a528f1
Merge pull request #221 from movesthatmatter/state-transformer-master…
GabrielCTroia Sep 26, 2024
1b054ac
ci(pretty-ms): :ferris_wheel: remove unneded lib
GabrielCTroia Sep 26, 2024
bd2e9d3
refactor(libs): :recycle: last cleanups
GabrielCTroia Sep 26, 2024
1278ca2
docs(changelog): :memo: update changelog
GabrielCTroia Sep 26, 2024
d154f92
chore(publishable-libs): :hammer: bump to v0.1.6
GabrielCTroia Sep 26, 2024
dcfa331
0.1.6
GabrielCTroia Sep 26, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 12 additions & 0 deletions .storybook/main.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import type { StorybookConfig } from '@storybook/core-common';

export const rootMain: StorybookConfig = {
stories: [],
addons: ['@storybook/addon-essentials'],
// webpackFinal: async (config, { configType }) => {
// // Make whatever fine-grained changes you need that should apply to all storybook configs

// // Return the altered config
// return config;
// },
};
14 changes: 14 additions & 0 deletions .storybook/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"extends": "../tsconfig.base.json",
"exclude": [
"../**/*.spec.js",
"../**/*.test.js",
"../**/*.spec.ts",
"../**/*.test.ts",
"../**/*.spec.tsx",
"../**/*.test.tsx",
"../**/*.spec.jsx",
"../**/*.test.jsx"
],
"include": ["../**/*"]
}
4 changes: 2 additions & 2 deletions apps/movex-demo/pages/chat/[chatId].tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { useMovexBoundResourceFromRid, useMovexClientId } from 'movex-react';
import { useMovexBoundResourceFromRid, useMovexClient } from 'movex-react';
import { useRouter } from 'next/router';
import { useMemo } from 'react';
import { toResourceIdentifierObj } from 'movex-core-util';
Expand All @@ -20,7 +20,7 @@ const ChatSystem: React.FC<Props> = () => {

// TODO: Validate the rid is correct inside useMovexBoundResouce
const boundResource = useMovexBoundResourceFromRid(movexConfig, rid);
const userId = useMovexClientId(movexConfig);
const userId = useMovexClient(movexConfig)?.id;

if (!(boundResource && userId)) {
return null;
Expand Down
4 changes: 4 additions & 0 deletions apps/movex-docs/pages/_meta.json
Original file line number Diff line number Diff line change
Expand Up @@ -24,5 +24,9 @@
"about": {
"title": "About",
"type": "page"
},
"changelog": {
"title": "Changelog",
"type": "page"
}
}
21 changes: 21 additions & 0 deletions apps/movex-docs/pages/changelog.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
# Changelog

## v0.1.6 (Sep 26 2024)

### New Features
- [x] Master Actions. [See Pull Request](https://github.com/movesthatmatter/movex/pull/216).
- [x] State Transformers. [See Pull Request](https://github.com/movesthatmatter/movex/pull/218).
- [x] Add ability to disconenect an older client connection (for same client id) in favor of the newer one

### Improvements
- [x] Improve the Connection Events. [See Pull Request](https://github.com/movesthatmatter/movex/pull/220).

### Bug Fixes
- [x] State not re-synching after a forwardAction checksum mismatch.

### Breaking
- none

## v0.1.5 (July 11 2024)
- [x] Add ability to pass in Client Info Object and sync it to all peers
- [x] Improve Logs
1 change: 1 addition & 0 deletions changelog.md
2 changes: 1 addition & 1 deletion libs/movex-core-util/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "movex-core-util",
"version": "0.1.5",
"version": "0.1.6",
"description": "Movex Core Util is the library of utilities for Movex",
"license": "MIT",
"author": {
Expand Down
3 changes: 1 addition & 2 deletions libs/movex-core-util/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,10 @@ export * from './lib/misc';
export * from './lib/domain';
export * from './lib/Observable/Observable';
export * from './lib/EventEmitter';
export * from './lib/ScketIOEmitter';
export * from './lib/Logsy';
export * from './lib/action';
export * from './lib/reducer';
export * from './lib/core-types';
export * from './lib/public-types';
export * from './lib/checkedState';
export * from './lib/io';
export * from './lib/masterContext';
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import type { EventMap } from 'typed-emitter';
import type { EmptyFn } from './core-types';
import type { EmptyFn } from '../core-types';

export const emptyFn: EmptyFn = () => {};

Expand Down Expand Up @@ -34,4 +34,9 @@ export interface EventEmitter<TEventMap extends EventMap> {
event: E,
request: Parameters<TEventMap[E]>[0]
): Promise<ReturnType<TEventMap[E]>>;

disconnect(): void;

onConnect(fn: () => void): EmptyFn;
onDisconnect(fn: () => void): EmptyFn;
}
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,10 @@ import type {
IOPayloadResult,
MovexClient,
ResourceIdentifier,
ResourceIdentifierStr,
SanitizedMovexClient,
} from '../core-types';
import { MovexMasterContext } from '../masterContext';
// import { MovexMasterContext } from '../reducer';

export type IOEvents<
TState = unknown,
Expand Down Expand Up @@ -72,37 +73,49 @@ export type IOEvents<
rid: ResourceIdentifier<TResourceType>;
action: ActionOrActionTupleFromAction<A>;
}) => IOPayloadResult<
| {
reconciled?: false;
nextChecksum: Checksum;
}
| ({
reconciled: true;
} & CheckedReconciliatoryActions<A>),
(
| {
type: 'ack';
nextChecksum: Checksum;
}
| {
type: 'masterActionAck';
// nextChecksum: Checksum;
nextCheckedAction: ToCheckedAction<A>;
}
| ({
type: 'reconciliation';
} & CheckedReconciliatoryActions<A>)
) & {
masterContext: MovexMasterContext;
},
'MasterResourceInexistent' | string
>; // Type the other errors

/**
* The following events are directed from Master to Client
* */
// @deprecate in favor ofClientReady
setClientId: (clientId: string) => void;
onReady: (p: SanitizedMovexClient) => void;

onClientReady: (client: SanitizedMovexClient) => void;
// onClockSync: (p: undefined) => IOPayloadResult<number, unknown>; // acknowledges the client timestamp

onFwdAction: (
payload: {
rid: ResourceIdentifier<TResourceType>;
masterContext: MovexMasterContext;
} & ToCheckedAction<A>
) => IOPayloadResult<void, unknown>;
onReconciliateActions: (
payload: {
rid: ResourceIdentifier<TResourceType>;
masterContext: MovexMasterContext;
} & CheckedReconciliatoryActions<A>
) => IOPayloadResult<void, unknown>;
onResourceSubscriberAdded: (p: {
rid: ResourceIdentifier<TResourceType>;
client: Pick<MovexClient, 'id' | 'info'>;
client: SanitizedMovexClient;
// TODO: Make required after it works
masterContext: MovexMasterContext;
// clientId: MovexClient['id'];
}) => IOPayloadResult<
void,
Expand All @@ -120,6 +133,7 @@ export type IOEvents<
* The following events are by-directional (from Client to Master and vice-versa)
* */

// They need to be different than ping/pong because those are native to socket.io
ping: () => IOPayloadResult<void, unknown>;
pong: () => IOPayloadResult<void, unknown>;
};
Original file line number Diff line number Diff line change
@@ -1,25 +1,33 @@
import { Err, Ok } from 'ts-results';
import { globalLogsy } from './Logsy';
import { globalLogsy } from '../Logsy';
import type { Socket as ServerSocket } from 'socket.io';
import type { Socket as ClientSocket } from 'socket.io-client';
import type { EventMap } from 'typed-emitter';
import type { EventEmitter } from './EventEmitter';
import type { UnsubscribeFn, WsResponseResultPayload } from './core-types';
import type { UnsubscribeFn, WsResponseResultPayload } from '../core-types';

export type SocketIO = ServerSocket | ClientSocket;

const logsy = globalLogsy.withNamespace('[SocketIOEmitter]');

export class SocketIOEmitter<TEventMap extends EventMap>
implements EventEmitter<TEventMap>
export class SocketIOEmitter<
TEventMap extends EventMap,
TSocketIO extends SocketIO = ServerSocket | ClientSocket
> implements EventEmitter<TEventMap>
{
protected config: {
waitForResponseMs: number;
};

constructor(
private socket: SocketIO,
private config: {
protected socket: TSocketIO,
config?: {
waitForResponseMs?: number;
} = {}
}
) {
this.config.waitForResponseMs = this.config.waitForResponseMs || 15 * 1000;
this.config = {
waitForResponseMs: config?.waitForResponseMs || 15 * 1000,
};
}

on<E extends keyof TEventMap>(
Expand Down Expand Up @@ -149,8 +157,36 @@ export class SocketIOEmitter<TEventMap extends EventMap>
);
}).catch((e) => e) as any;
}

onConnect(fn: () => void) {
this.socket.on('connect', fn);

return () => {
this.socket.off('connect', fn);
};
}

onDisconnect(fn: () => void) {
this.socket.on('disconnect', fn);

return () => {
this.socket.off('disconnect', fn);
};
}

disconnect(): void {
this.socket.disconnect();
}
}

/**
* TODO: Deprecate this in favor of using the native timeout See https://socket.io/docs/v4/emitting-events/#with-timeout
*
* @param onSuccess
* @param onTimeout
* @param timeout
* @returns
*/
const withTimeout = (
onSuccess: (...args: any[]) => void,
onTimeout: () => void,
Expand Down
3 changes: 3 additions & 0 deletions libs/movex-core-util/src/lib/EventEmitter/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export * from './EventEmitter';
export * from './IOEvents';
export * from './ScketIOEmitter';
72 changes: 67 additions & 5 deletions libs/movex-core-util/src/lib/action.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,13 @@ import { isObject, keyInObject } from './misc';

// TODO: ith the new Reducer Refactoring, all of the action with collection map and generic actions can be removed I believe

/**
* TODO: 18.08.2024 - This file needs a restructuring:
* - there are too many types, many of them aren't used or are intersecting with others
* - others are just confusing and create more issues in understanding (AnyAction vs GenericAction - which one is what???)
* - others are remnants of long past times (e..g all of the action with collection map and generic actions can be removed I believe)
*/

export type BaseAction<
TType extends string,
TPayload = undefined
Expand All @@ -27,9 +34,20 @@ export type PublicAction<
isPrivate?: false;
};

export type MasterAction<TType extends string, TPayload = undefined> =
| (PrivateAction<TType, TPayload> & {
_isMaster: true; // Note: This is only meant for internal useage
})
| (PublicAction<TType, TPayload> & {
_isMaster: true; // Note: This is only meant for internal useage
});

export type Action<TType extends string, TPayload = undefined> =
| PublicAction<TType, TPayload>
| PrivateAction<TType, TPayload>;
| PrivateAction<TType, TPayload>
| MasterAction<TType, TPayload>;

export type AnyMasterAction = MasterAction<string>;

export type ActionWithAnyPayload<TType extends string> = Action<TType, unknown>;

Expand All @@ -56,10 +74,14 @@ export type AnyPublicActionOf<

export type GenericPrivateAction = PrivateAction<string, unknown>;
export type GenericPublicAction = PublicAction<string, unknown>;
export type GenericMasterAction = MasterAction<string, unknown>;

export type GenericAction = GenericPrivateAction | GenericPublicAction;
export type GenericAction =
| GenericPrivateAction
| GenericPublicAction
| GenericMasterAction;

export type AnyAction = Action<string>;
export type AnyAction = Action<string> | GenericAction;

export type UnknownAction = Action<string, unknown>;

Expand Down Expand Up @@ -99,6 +121,10 @@ export type ToPublicAction<A extends AnyAction> = A & {
isPrivate?: false;
};

export type ToMasterAction<A extends AnyAction> = A & {
_isMaster: true;
};

export type CheckedReconciliatoryActions<A extends AnyAction> = {
actions: ToPublicAction<A>[];
finalChecksum: Checksum;
Expand Down Expand Up @@ -144,7 +170,7 @@ export type ActionCreatorsMapBase = {
[k in string]: ReturnType<typeof createActionCreator>;
};

export type ActionTupleFrom<TAction extends AnyAction> = [
export type ActionTupleFrom<TAction extends AnyAction | AnyMasterAction> = [
ToPrivateAction<TAction>,
ToPublicAction<TAction>
];
Expand Down Expand Up @@ -267,6 +293,42 @@ export function createActionCreator<
});
}

export const isAction = (a: unknown): a is AnyAction => {
export const isAction = (
a: ActionOrActionTupleFromAction<AnyAction> | AnyAction
): a is AnyAction => {
// TODO: This isn't a super thorough check, but if the input is limited
// to only action or ActionTuple should be enough
return isObject(a) && keyInObject(a, 'type');
};

export const isMasterAction = (
a: ActionOrActionTupleFromAction<AnyAction> | AnyAction
): a is AnyMasterAction => {
// TODO: This isn't a super thorough check, but if the input is limited
// to only action or ActionTuple should be enough
return isAction(a) && keyInObject(a, '_isMaster') && a._isMaster === true;
};

export const toMasterAction = <TAction extends AnyAction>(
action: TAction
): ToMasterAction<TAction> => ({
...action,
_isMaster: true,
});

export const toMasterActionFromActionOrTuple = <TAction extends AnyAction>(
actionOrActionTuple: ActionOrActionTupleFromAction<TAction>
) => {
return (
isAction(actionOrActionTuple)
? toMasterAction(actionOrActionTuple)
: // TODO: In the case of a tuple, there is not enough information
// so I'm just making them both a masterAction, but I should only make the one that is needed actually
// - this isn't the worst possible thing as if there's nothing to parse nothing will parse
// and the client will simply attempt to run again with the same
[
toMasterAction(actionOrActionTuple[0]),
toMasterAction(actionOrActionTuple[1]),
]
) as ActionOrActionTupleFromAction<ToMasterAction<TAction>>;
};
Loading
Loading